mono::object CScriptbind_Entity::GetEntityLinks(IEntity *pEntity) { // the first link IEntityLink *pLink = pEntity->GetEntityLinks(); IMonoArray *pDynArray = CreateDynamicMonoArray(); while(pLink != nullptr) { pDynArray->InsertAny(reinterpret_cast<intptr_t>(pLink)); pLink = pLink->next; } return pDynArray->GetManagedObject(); }
IMonoAssembly *CScriptDomain::LoadAssembly(const char *file, bool shadowCopy, bool convertPdbToMdb) { const char *path; if(shadowCopy) path = GetTempPath().append(PathUtil::GetFile(file)); else path = file; for each(auto assembly in m_assemblies) { if(!strcmp(path, assembly->GetPath())) return assembly; } if(shadowCopy) CopyFile(file, path, false); string sAssemblyPath(path); #ifndef _RELEASE if(g_pMonoCVars->mono_generateMdbIfPdbIsPresent != 0 && convertPdbToMdb && sAssemblyPath.find("pdb2mdb")==-1) { if (IMonoAssembly *pDebugDatabaseCreator = static_cast<CScriptSystem *>(GetMonoScriptSystem())->GetDebugDatabaseCreator()) { if(IMonoClass *pDriverClass = pDebugDatabaseCreator->GetClass("Driver", "")) { if(IMonoMethod *pConvertMethod = pDriverClass->GetMethod("Convert", 1)) { IMonoArray *pArgs = CreateMonoArray(1); pArgs->Insert(path); pConvertMethod->InvokeArray(nullptr, pArgs); SAFE_RELEASE(pArgs); } } } } #endif if(MonoAssembly *pMonoAssembly = mono_domain_assembly_open(m_pDomain, path)) { CScriptAssembly *pAssembly = new CScriptAssembly(this, mono_assembly_get_image(pMonoAssembly), path); m_assemblies.push_back(pAssembly); return pAssembly; } return nullptr; }
bool CScriptbind_Entity::OnRemove(IEntity *pIEntity) { if(IMonoClass *pEntityClass = g_pScriptSystem->GetCryBraryAssembly()->GetClass("Entity")) { IMonoArray *pArgs = CreateMonoArray(1); pArgs->Insert(pIEntity->GetId()); auto result = pEntityClass->InvokeArray(NULL, "InternalRemove", pArgs)->Unbox<bool>(); SAFE_RELEASE(pArgs); if(!result) return false; } return true; }
mono::object CScriptbind_Physics::SimulateExplosion(pe_explosion explosion) { gEnv->pPhysicalWorld->SimulateExplosion(&explosion); if(explosion.nAffectedEnts > 0) { IMonoArray *pAffectedEnts = CreateMonoArray(explosion.nAffectedEnts); for(int i = 0; i < explosion.nAffectedEnts; i++) pAffectedEnts->InsertNativePointer(explosion.pAffectedEnts[i]); pAffectedEnts->Release(); return pAffectedEnts->GetManagedObject(); } return NULL; }
bool CScriptbind_Entity::OnRemove(IEntity *pIEntity) { if(m_pEntityClass == nullptr) return true; IMonoArray *pArgs = CreateMonoArray(1); pArgs->Insert(pIEntity->GetId()); IMonoObject *pResult = *m_pEntityClass->GetMethod("InternalRemove", 1)->InvokeArray(NULL, pArgs); auto result = pResult->Unbox<bool>(); SAFE_RELEASE(pArgs); SAFE_RELEASE(pResult); return result; return true; }
mono::object CScriptbind_Entity::GetEntitiesInBox(AABB bbox, int objTypes) { IPhysicalEntity **pEnts = nullptr; IMonoClass *pEntityIdClass = GetMonoScriptSystem()->GetCryBraryAssembly()->GetClass("EntityId"); int numEnts = gEnv->pPhysicalWorld->GetEntitiesInBox(bbox.min, bbox.max, pEnts, objTypes); IMonoArray *pEntities = CreateDynamicMonoArray(); for(int i = 0; i < numEnts; i++) pEntities->InsertMonoObject(pEntityIdClass->BoxObject(&mono::entityId(gEnv->pPhysicalWorld->GetPhysicalEntityId(pEnts[i])))); auto result = pEntities->GetManagedObject(); pEntities->Release(); return result; }
void CCryScriptInstance::OnReloadComplete() { if(m_scriptId == 0) return; IMonoObject *pScriptManager = g_pScriptSystem->GetScriptManager(); IMonoArray *pArgs = CreateMonoArray(2); pArgs->Insert(m_scriptId); pArgs->Insert(m_flags); if(mono::object result = pScriptManager->GetClass()->InvokeArray(pScriptManager->GetManagedObject(), "GetScriptInstanceById", pArgs)) { SetManagedObject((MonoObject *)result, true); } else MonoWarning("Failed to locate script instance %i after reload!", m_scriptId); pArgs->Release(); }
mono::object CScriptbind_Entity::GetEntitiesInBox(AABB bbox, int objTypes) { IPhysicalEntity **pEnts = nullptr; IMonoClass *pEntityIdClass = g_pScriptSystem->GetCryBraryAssembly()->GetClass("EntityId"); int numEnts = gEnv->pPhysicalWorld->GetEntitiesInBox(bbox.min, bbox.max, pEnts, objTypes); if(numEnts > 0) { IMonoArray *pEntities = CreateMonoArray(numEnts); for(int i = 0; i < numEnts; i++) pEntities->Insert(pEntityIdClass->BoxObject(&mono::entityId(gEnv->pPhysicalWorld->GetPhysicalEntityId(pEnts[i])))); return pEntities->GetManagedObject(); } return nullptr; }
IMonoAssembly *CScriptDomain::LoadAssembly(const char *file, bool shadowCopy, bool convertPdbToMdb) { const char *path; if(shadowCopy) path = GetTempPath().append(PathUtil::GetFile(file)); else path = file; for each(auto assembly in m_assemblies) { if(!strcmp(path, assembly->GetPath())) return assembly; } if(shadowCopy) CopyFile(file, path, false); string sAssemblyPath(path); #ifndef _RELEASE if(convertPdbToMdb && sAssemblyPath.find("pdb2mdb")==-1) { if(IMonoAssembly *pDebugDatabaseCreator = g_pScriptSystem->GetDebugDatabaseCreator()) { if(IMonoClass *pDriverClass = pDebugDatabaseCreator->GetClass("Driver", "")) { IMonoArray *pArgs = CreateMonoArray(1); pArgs->Insert(path); pDriverClass->InvokeArray(NULL, "Convert", pArgs); SAFE_RELEASE(pArgs); } } } #endif MonoAssembly *pMonoAssembly = mono_domain_assembly_open(m_pDomain, path); CRY_ASSERT(pMonoAssembly); CScriptAssembly *pAssembly = new CScriptAssembly(this, mono_assembly_get_image(pMonoAssembly), path); m_assemblies.push_back(pAssembly); return pAssembly; }
bool CMonoEntityExtension::Init(IGameObject *pGameObject) { SetGameObject(pGameObject); pGameObject->EnablePhysicsEvent( true, eEPE_OnPostStepImmediate ); if (!GetGameObject()->BindToNetwork()) return false; IEntity *pEntity = GetEntity(); IEntityClass *pEntityClass = pEntity->GetClass(); m_pScript = g_pScriptSystem->InstantiateScript(pEntityClass->GetName(), eScriptFlag_Entity); IMonoClass *pEntityInfoClass = g_pScriptSystem->GetCryBraryAssembly()->GetClass("EntityInitializationParams", "CryEngine.Native"); SMonoEntityInfo entityInfo(pEntity); IMonoArray *pArgs = CreateMonoArray(1); pArgs->InsertMonoObject(pEntityInfoClass->BoxObject(&entityInfo)); g_pScriptSystem->InitializeScriptInstance(m_pScript, pArgs); pArgs->Release(); int numProperties; auto pProperties = static_cast<CEntityPropertyHandler *>(pEntityClass->GetPropertyHandler())->GetQueuedProperties(pEntity->GetId(), numProperties); if(pProperties) { for(int i = 0; i < numProperties; i++) { auto queuedProperty = pProperties[i]; SetPropertyValue(queuedProperty.propertyInfo, queuedProperty.value.c_str()); } } m_bInitialized = true; return true; }
void CFlowNode::GetConfiguration(SFlowNodeConfig &config) { CRY_ASSERT(m_pScript); if(IMonoObject *pResult = m_pScript->CallMethod("GetNodeConfig")) { SMonoNodeConfig monoConfig = pResult->Unbox<SMonoNodeConfig>(); config.nFlags |= monoConfig.flags; config.sDescription = _HELP(ToCryString(monoConfig.description)); config.SetCategory(monoConfig.category); m_cloneType = monoConfig.cloneType; // Ports static const int MAX_NODE_PORT_COUNT = 20; SInputPortConfig nullptrConfig = {0}; SOutputPortConfig nullptrOutputConfig = {0}; IMonoArray *pInputPorts = *monoConfig.inputs; auto pInputs = new SInputPortConfig[MAX_NODE_PORT_COUNT]; for(int i = 0; i < pInputPorts->GetSize(); i++) pInputs[i] = pInputPorts->GetItem(i)->Unbox<SMonoInputPortConfig>().Convert(); for(int i = pInputPorts->GetSize(); i < MAX_NODE_PORT_COUNT; i++) pInputs[i] = nullptrConfig; config.pInputPorts = pInputs; SAFE_RELEASE(pInputPorts); // Convert MonoArray type to our custom CScriptArray for easier handling. IMonoArray *pOutputPorts = *monoConfig.outputs; auto pOutputs = new SOutputPortConfig[MAX_NODE_PORT_COUNT]; for(int i = 0; i < pOutputPorts->GetSize(); i++) pOutputs[i] = pOutputPorts->GetItem(i)->Unbox<SMonoOutputPortConfig>().Convert(); for(int i = pOutputPorts->GetSize(); i < MAX_NODE_PORT_COUNT; i++) pOutputs[i] = nullptrOutputConfig; config.pOutputPorts = pOutputs; SAFE_RELEASE(pOutputPorts); } }
int CScriptbind_Physics::RayWorldIntersection(Vec3 origin, Vec3 dir, int objFlags, unsigned int flags, int maxHits, mono::object skipEntities, mono::object &hits) { IPhysicalEntity **pSkipEnts = NULL; int numSkipEnts = 0; if(skipEntities) { IMonoArray *pSkipEntities = *skipEntities; numSkipEnts = pSkipEntities->GetSize(); pSkipEnts = new IPhysicalEntity*[numSkipEnts]; for(int i = 0; i < numSkipEnts; i++) { IMonoObject *pItem = *pSkipEntities->GetItem(i); #ifndef RELEASE if(!pItem) g_pScriptSystem->GetCryBraryAssembly()->GetException("CryEngine", "NullPointerException")->Throw(); #endif pSkipEnts[i] = pItem->Unbox<IPhysicalEntity *>(); SAFE_RELEASE(pItem); } pSkipEntities->Release(); } ray_hit *pHits = new ray_hit[maxHits]; int numHits = gEnv->pPhysicalWorld->RayWorldIntersection(origin, dir, objFlags, flags, pHits, maxHits, pSkipEnts, numSkipEnts); SAFE_DELETE_ARRAY(pSkipEnts); if(numHits > 0) { IMonoClass *pRayHitClass = g_pScriptSystem->GetCryBraryAssembly()->GetClass("RaycastHit"); IMonoArray *pRayHits = CreateMonoArray(numHits);//, pRayHitClass); for(int i = 0; i < numHits; i++) pRayHits->InsertMonoObject(pRayHitClass->BoxObject(&pHits[i])); hits = pRayHits->GetManagedObject(); pRayHits->Release(); } delete[] pHits; return numHits; }
void CMonoEntityExtension::FullSerialize(TSerialize ser) { IEntity *pEntity = GetEntity(); ser.BeginGroup("Properties"); auto pPropertyHandler = static_cast<CEntityPropertyHandler *>(pEntity->GetClass()->GetPropertyHandler()); for(int i = 0; i < pPropertyHandler->GetPropertyCount(); i++) { if(ser.IsWriting()) { IEntityPropertyHandler::SPropertyInfo propertyInfo; pPropertyHandler->GetPropertyInfo(i, propertyInfo); ser.Value(propertyInfo.name, pPropertyHandler->GetProperty(pEntity, i)); } else { IEntityPropertyHandler::SPropertyInfo propertyInfo; pPropertyHandler->GetPropertyInfo(i, propertyInfo); char *propertyValue = nullptr; ser.ValueChar(propertyInfo.name, propertyValue, 0); pPropertyHandler->SetProperty(pEntity, i, propertyValue); } } ser.EndGroup(); ser.BeginGroup("ManagedEntity"); IMonoArray *pArgs = CreateMonoArray(1); pArgs->InsertNativePointer(&ser); m_pScript->GetClass()->InvokeArray(m_pScript->GetManagedObject(), "InternalFullSerialize", pArgs); pArgs->Release(); ser.EndGroup(); }
void CMonoFlowNode::GetConfiguration(SFlowNodeConfig &config) { CRY_ASSERT(m_pScript); if(mono::object result = m_pScript->CallMethod("GetNodeConfig")) { IMonoObject *pResult = *result; SMonoNodeConfig monoConfig = pResult->Unbox<SMonoNodeConfig>(); config.nFlags |= monoConfig.flags; config.sDescription = _HELP(ToCryString(monoConfig.description)); config.SetCategory(monoConfig.category); m_flags = config.nFlags; m_cloneType = monoConfig.cloneType; // Ports IMonoArray *pInputPorts = *monoConfig.inputs; int numInputs = pInputPorts->GetSize(); auto pInputs = new SInputPortConfig[numInputs + 1]; for(int i = 0; i < numInputs; i++) { IMonoObject *pInputObject = *pInputPorts->GetItem(i); pInputs[i] = pInputObject->Unbox<SMonoInputPortConfig>().Convert(); SAFE_RELEASE(pInputObject); } SInputPortConfig nullInputPortConfig = {0}; pInputs[numInputs] = nullInputPortConfig; config.pInputPorts = pInputs; SAFE_RELEASE(pInputPorts); IMonoArray *pOutputPorts = *monoConfig.outputs; int numOutputs = pOutputPorts->GetSize(); auto pOutputs = new SOutputPortConfig[numOutputs + 1]; for(int i = 0; i < numOutputs; i++) { IMonoObject *pOutputObject = *pOutputPorts->GetItem(i); pOutputs[i] = pOutputObject->Unbox<SMonoOutputPortConfig>().Convert(); SAFE_RELEASE(pOutputObject); } SOutputPortConfig nullOutputPortConfig = {0}; pOutputs[numOutputs] = nullOutputPortConfig; config.pOutputPorts = pOutputs; SAFE_RELEASE(pOutputPorts); SAFE_RELEASE(pResult); } }
void CScriptbind_ActorSystem::OnSpawn(IEntity *pEntity,SEntitySpawnParams ¶ms) { EMonoActorType actorType = GetMonoActorType(pEntity->GetClass()->GetName()); if(actorType != EMonoActorType_None) { if(IActor *pActor = static_cast<CScriptSystem *>(GetMonoScriptSystem())->GetIGameFramework()->GetIActorSystem()->GetActor(pEntity->GetId())) { ICryScriptInstance *pScript = GetMonoScriptSystem()->InstantiateScript(pEntity->GetClass()->GetName(), eScriptFlag_Actor); IMonoClass *pActorInfoClass = GetMonoScriptSystem()->GetCryBraryAssembly()->GetClass("ActorInitializationParams", "CryEngine.Native"); SMonoActorInfo actorInfo(pActor); IMonoArray *pArgs = CreateMonoArray(1); pArgs->InsertMonoObject(pActorInfoClass->BoxObject(&actorInfo)); static_cast<CScriptSystem *>(GetMonoScriptSystem())->InitializeScriptInstance(pScript, pArgs); SAFE_RELEASE(pArgs); } } }
mono::object CScriptbind_Entity::QueryProximity(AABB box, mono::string className, uint32 nEntityFlags) { SEntityProximityQuery query; if(className != nullptr) query.pEntityClass = gEnv->pEntitySystem->GetClassRegistry()->FindClass(ToCryString(className)); query.box = box; query.nEntityFlags = nEntityFlags; gEnv->pEntitySystem->QueryProximity(query); IMonoClass *pEntityIdClass = GetMonoScriptSystem()->GetCryBraryAssembly()->GetClass("EntityId"); IMonoArray *pEntities = CreateDynamicMonoArray(); for(int i = 0; i < query.nCount; i++) pEntities->InsertMonoObject(pEntityIdClass->BoxObject(&mono::entityId(query.pEntities[i]->GetId()))); auto result = pEntities->GetManagedObject(); pEntities->Release(); return result; }
bool CMonoFlowNode::CreatedNode(TFlowNodeId id, const char *name, TFlowNodeTypeId typeId, IFlowNodePtr pNode) { if(pNode==this) { m_id = id; m_graphId = m_pActInfo->pGraph->GetGraphId(); const char *typeName = gEnv->pFlowSystem->GetTypeName(typeId); ICryScriptInstance *pScript = GetMonoScriptSystem()->InstantiateScript(gEnv->pFlowSystem->GetTypeName(typeId), eScriptFlag_FlowNode); IMonoClass *pNodeInfo = GetMonoScriptSystem()->GetCryBraryAssembly()->GetClass("NodeInitializationParams", "CryEngine.Flowgraph.Native"); IMonoArray *pArgs = CreateMonoArray(1); pArgs->InsertMonoObject(pNodeInfo->BoxObject(&SMonoNodeInfo(this, id, m_graphId))); mono::object result = static_cast<CScriptSystem *>(GetMonoScriptSystem())->InitializeScriptInstance(pScript, pArgs); pArgs->Release(); m_pScript = pScript; m_scriptId = pScript->GetId(); if(result) { IMonoObject *pResult = *result; bool bResult = pResult->Unbox<bool>(); SAFE_RELEASE(pResult); return bResult; } CryLogAlways("Failed to create node %s", gEnv->pFlowSystem->GetTypeName(typeId)); return false; } return true; }
mono::object CScriptbind_Entity::GetEntitiesByClass(mono::string _class) { IEntityClass *pDesiredClass = gEnv->pEntitySystem->GetClassRegistry()->FindClass(ToCryString(_class)); IEntityItPtr pIt = gEnv->pEntitySystem->GetEntityIterator(); IMonoClass *pEntityIdClass = GetMonoScriptSystem()->GetCryBraryAssembly()->GetClass("EntityId"); IMonoArray *pEntities = CreateDynamicMonoArray(); pIt->MoveFirst(); while(!pIt->IsEnd()) { if(IEntity *pEntity = pIt->Next()) { if(pEntity->GetClass() == pDesiredClass) pEntities->InsertMonoObject(pEntityIdClass->BoxObject(&mono::entityId(pEntity->GetId()))); } } auto result = pEntities->GetManagedObject(); pEntities->Release(); return result; }
ICryScriptInstance *CScriptSystem::InstantiateScript(const char *scriptName, EMonoScriptFlags scriptFlags, IMonoArray *pConstructorParameters, bool throwOnFail) { FUNCTION_PROFILER_FAST(GetISystem(), PROFILE_SCRIPT, gEnv->bProfilerEnabled); auto *pInstance = new CCryScriptInstance(scriptFlags); IMonoArray *pScriptCreationArgs = CreateMonoArray(5); pScriptCreationArgs->Insert(scriptName); pScriptCreationArgs->Insert(scriptFlags); pScriptCreationArgs->InsertNativePointer(pInstance); pScriptCreationArgs->InsertMonoObject((pConstructorParameters != nullptr ? pConstructorParameters->GetManagedObject() : nullptr)); pScriptCreationArgs->Insert(throwOnFail); auto result = m_pScriptManager->GetClass()->GetMethod("CreateScriptInstance", 5)->InvokeArray(m_pScriptManager->GetManagedObject(), pScriptCreationArgs); SAFE_RELEASE(pScriptCreationArgs); if(!result) return nullptr; pInstance->SetManagedObject((MonoObject *)result, true); if(scriptFlags & eScriptFlag_GameRules) { IMonoClass *pGameRulesInitParamsClass = m_pCryBraryAssembly->GetClass("GameRulesInitializationParams"); IMonoArray *pArgs = CreateMonoArray(1); SGameRulesInitializationParams params; pArgs->InsertMonoObject(pGameRulesInitParamsClass->BoxObject(¶ms)); InitializeScriptInstance(pInstance, pArgs); SAFE_RELEASE(pArgs); } for each(auto listener in m_listeners) listener->OnScriptInstanceCreated(scriptName, scriptFlags, pInstance); return pInstance; }
void CMonoEntityExtension::RMIParams::SerializeWith(TSerialize ser) { IMonoArray *pArgs; int length; if(args != nullptr) { pArgs = *args; length = pArgs->GetSize(); } else length = 0; ser.Value("length", length); ser.Value("methodName", methodName); ser.Value("targetId", targetId, 'eid'); if(length > 0) { if(ser.IsWriting()) { for(int i = 0; i < length; i++) { IMonoObject *pItem = *pArgs->GetItem(i); pItem->GetAnyValue().SerializeWith(ser); SAFE_RELEASE(pItem); } } else { pArgs = g_pScriptSystem->GetScriptDomain()->CreateArray(length); for(int i = 0; i < length; i++) { MonoAnyValue value; value.SerializeWith(ser); pArgs->InsertAny(value, i); } args = pArgs->GetManagedObject(); } pArgs->Release(); } }
mono::object CScriptbind_Entity::GetEntitiesByClasses(mono::object classes) { IMonoArray *pClassArray = *classes; int numClasses = pClassArray->GetSize(); IEntityClass **pClasses = new IEntityClass *[numClasses]; for(int i = 0; i < numClasses; i++) pClasses[i] = gEnv->pEntitySystem->GetClassRegistry()->FindClass(ToCryString((mono::string)pClassArray->GetManagedObject())); IEntityItPtr pIt = gEnv->pEntitySystem->GetEntityIterator(); IMonoClass *pEntityIdClass = GetMonoScriptSystem()->GetCryBraryAssembly()->GetClass("EntityId"); IMonoArray *pEntities = CreateDynamicMonoArray(); pIt->MoveFirst(); while(!pIt->IsEnd()) { if(IEntity *pEntity = pIt->Next()) { IEntityClass *pEntityClass = pEntity->GetClass(); for(int i = 0; i < numClasses; i++) { if(pEntityClass == pClasses[i]) { pEntities->InsertMonoObject(pEntityIdClass->BoxObject(&mono::entityId(pEntity->GetId()))); break; } } } } auto result = pEntities->GetManagedObject(); pEntities->Release(); return result; }
bool CScriptbind_Entity::RegisterEntityClass(SEntityRegistrationParams params) { const char *className = ToCryString(params.Name); if(gEnv->pEntitySystem->GetClassRegistry()->FindClass(className)) { MonoWarning("Aborting registration of entity class %s, a class with the same name already exists", className); return false; } std::vector<IEntityPropertyHandler::SPropertyInfo> properties; if(params.Folders != nullptr) { IMonoArray *pFolderArray = *params.Folders; int numFolders = pFolderArray->GetSize(); for (int iFolder = 0; iFolder < numFolders; ++iFolder) { IMonoObject *pFolderObject = pFolderArray->GetItem(iFolder); if(!pFolderObject) continue; auto folder = pFolderObject->Unbox<SMonoEntityPropertyFolder>(); if(folder.properties == nullptr) continue; bool bDefaultFolder = !strcmp(ToCryString(folder.name), "Default") && iFolder == 0; if(!bDefaultFolder) // first element contains properties not organized into folders { IEntityPropertyHandler::SPropertyInfo folderInfo; folderInfo.name = ToCryString(folder.name); folderInfo.type = IEntityPropertyHandler::FolderBegin; properties.push_back(folderInfo); } IMonoArray *pPropertyArray = *folder.properties; for(int iProperty = 0; iProperty < pPropertyArray->GetSize(); iProperty++) { IMonoObject *pPropertyObject = pPropertyArray->GetItem(iProperty); if(pPropertyObject == nullptr) continue; auto property = pPropertyObject->Unbox<SMonoEntityProperty>(); IEntityPropertyHandler::SPropertyInfo propertyInfo; propertyInfo.name = ToCryString(property.name); propertyInfo.description = ToCryString(property.description); propertyInfo.editType = ToCryString(property.editType); propertyInfo.type = property.type; propertyInfo.limits.min = property.limits.min; propertyInfo.limits.max = property.limits.max; properties.push_back(propertyInfo); } if(!bDefaultFolder) { IEntityPropertyHandler::SPropertyInfo folderInfo; folderInfo.name = ToCryString(folder.name); folderInfo.type = IEntityPropertyHandler::FolderEnd; properties.push_back(folderInfo); } } } IEntityClassRegistry::SEntityClassDesc entityClassDesc; entityClassDesc.flags = params.Flags; entityClassDesc.sName = className; entityClassDesc.editorClassInfo.sCategory = ToCryString(params.Category); if(params.EditorHelper != nullptr) entityClassDesc.editorClassInfo.sHelper = ToCryString(params.EditorHelper); if(params.EditorIcon != nullptr) entityClassDesc.editorClassInfo.sIcon = ToCryString(params.EditorIcon); m_monoEntityClasses.push_back(className); bool result = gEnv->pEntitySystem->GetClassRegistry()->RegisterClass(new CEntityClass(entityClassDesc, properties)); static SMonoEntityCreator creator; gEnv->pGameFramework->GetIGameObjectSystem()->RegisterExtension(className, &creator, nullptr); return result; }
bool CScriptbind_Entity::RegisterEntityClass(SEntityRegistrationParams params) { const char *className = ToCryString(params.Name); if(gEnv->pEntitySystem->GetClassRegistry()->FindClass(className)) { MonoWarning("Aborting registration of entity class %s, a class with the same name already exists", className); return false; } int numProperties = 0; SMonoEntityPropertyInfo *pProperties; if(params.Properties != nullptr) { IMonoArray *pPropertyArray = *params.Properties; numProperties = pPropertyArray->GetSize(); pProperties = new SMonoEntityPropertyInfo[numProperties]; for (int iProperty = 0; iProperty < numProperties; iProperty++) { mono::object propertyObject = pPropertyArray->GetItem(iProperty); if(propertyObject == nullptr) continue; auto property = *(SMonoEntityProperty *)mono_object_unbox((MonoObject *)propertyObject); SMonoEntityPropertyInfo propertyInfo; propertyInfo.info.name = ToCryString(property.name); propertyInfo.info.description = ToCryString(property.description); propertyInfo.info.editType = ToCryString(property.editType); propertyInfo.info.type = property.type; propertyInfo.info.limits.min = property.limits.min; propertyInfo.info.limits.max = property.limits.max; propertyInfo.defaultValue = ToCryString(property.defaultValue); pProperties[iProperty] = propertyInfo; } } IEntityClassRegistry::SEntityClassDesc entityClassDesc; entityClassDesc.flags = params.Flags; entityClassDesc.sName = className; entityClassDesc.editorClassInfo.sCategory = ToCryString(params.Category); if(params.EditorHelper != nullptr) entityClassDesc.editorClassInfo.sHelper = ToCryString(params.EditorHelper); if(params.EditorIcon != nullptr) entityClassDesc.editorClassInfo.sIcon = ToCryString(params.EditorIcon); m_monoEntityClasses.push_back(className); bool result = gEnv->pEntitySystem->GetClassRegistry()->RegisterClass(new CEntityClass(entityClassDesc, pProperties, numProperties)); static SMonoEntityCreator creator; static_cast<CScriptSystem *>(GetMonoScriptSystem())->GetIGameFramework()->GetIGameObjectSystem()->RegisterExtension(className, &creator, nullptr); return result; }
bool CMonoActor::NetSerialize( TSerialize ser, EEntityAspects aspect, uint8 profile, int pflags ) { if (aspect == eEA_Physics) { pe_type type = PE_NONE; switch (profile) { case eAP_NotPhysicalized: type = PE_NONE; break; case eAP_Spectator: type = PE_LIVING; break; case eAP_Alive: type = PE_LIVING; break; case eAP_Sleep: type = PE_ARTICULATED; break; case eAP_Frozen: type = PE_RIGID; break; case eAP_Ragdoll: type = PE_ARTICULATED; break; case eAP_Linked: //if actor is attached to a vehicle - don't serialize actor physics additionally return true; break; default: return false; } // TODO: remove this when craig fixes it in the network system if (profile==eAP_Spectator) { int x=0; ser.Value("unused", x, 'skip'); } else if (profile==eAP_Sleep) { int x=0; ser.Value("unused1", x, 'skip'); ser.Value("unused2", x, 'skip'); } if (type == PE_NONE) return true; IEntityPhysicalProxy * pEPP = (IEntityPhysicalProxy *) GetEntity()->GetProxy(ENTITY_PROXY_PHYSICS); if (ser.IsWriting()) { if (!pEPP || !pEPP->GetPhysicalEntity() || pEPP->GetPhysicalEntity()->GetType() != type) { gEnv->pPhysicalWorld->SerializeGarbageTypedSnapshot( ser, type, 0 ); return true; } } else if (!pEPP) { return false; } // PLAYERPREDICTION if(type!=PE_LIVING) { pEPP->SerializeTyped( ser, type, pflags ); } // ~PLAYERPREDICTION } ser.BeginGroup("ManagedActor"); IMonoArray *pArgs = CreateMonoArray(4); pArgs->InsertNativePointer(&ser); pArgs->Insert(aspect); pArgs->Insert(profile); pArgs->Insert(pflags); m_pScript->GetClass()->InvokeArray(m_pScript, "InternalNetSerialize", pArgs); ser.EndGroup(); return true; }
void CEntityEventHandler::HandleEntityEvent(EEntityType type, SEntityEvent &event, IEntity *pEntity, mono::object managedObject) { switch(event.event) { case ENTITY_EVENT_RESET: { bool enterGamemode = event.nParam[0]==1; if(!enterGamemode && pEntity->GetFlags() & ENTITY_FLAG_NO_SAVE) { gEnv->pEntitySystem->RemoveEntity(pEntity->GetId()); return; } IMonoArray *pParams = CreateMonoArray(1); pParams->Insert(enterGamemode); m_pClass[type]->GetMethod("OnEditorReset", 1)->InvokeArray(managedObject, pParams); SAFE_RELEASE(pParams); } break; case ENTITY_EVENT_COLLISION: { EventPhysCollision *pCollision = (EventPhysCollision *)event.nParam[0]; SMonoColliderInfo source = SMonoColliderInfo(pCollision, 0); SMonoColliderInfo target = SMonoColliderInfo(pCollision, 1); IMonoClass *pColliderInfoClass = g_pScriptSystem->GetCryBraryAssembly()->GetClass("ColliderInfo"); IMonoArray *pArgs = CreateMonoArray(6); pArgs->InsertMonoObject(pColliderInfoClass->BoxObject(&source)); pArgs->InsertMonoObject(pColliderInfoClass->BoxObject(&target)); pArgs->Insert(pCollision->pt); pArgs->Insert(pCollision->n); pArgs->Insert(pCollision->penetration); pArgs->Insert(pCollision->radius); m_pClass[type]->GetMethod("OnCollision", 6)->InvokeArray(managedObject, pArgs); SAFE_RELEASE(pArgs); } break; case ENTITY_EVENT_START_GAME: m_pClass[type]->GetMethod("OnStartGame")->Invoke(managedObject); break; case ENTITY_EVENT_START_LEVEL: m_pClass[type]->GetMethod("OnStartLevel")->Invoke(managedObject); break; case ENTITY_EVENT_LEVEL_LOADED: m_pClass[type]->GetMethod("OnLevelLoaded")->Invoke(managedObject); break; case ENTITY_EVENT_ENTERAREA: m_pClass[type]->GetMethod("OnEnterArea", 3)->Call(managedObject, (EntityId)event.nParam[0], (int)event.nParam[1], (EntityId)event.nParam[2]); break; case ENTITY_EVENT_MOVEINSIDEAREA: m_pClass[type]->GetMethod("OnMoveInsideArea", 3)->Call(managedObject, (EntityId)event.nParam[0], (int)event.nParam[1], (EntityId)event.nParam[2]); break; case ENTITY_EVENT_LEAVEAREA: m_pClass[type]->GetMethod("OnLeaveArea", 3)->Call(managedObject, (EntityId)event.nParam[0], (int)event.nParam[1], (EntityId)event.nParam[2]); break; case ENTITY_EVENT_ENTERNEARAREA: m_pClass[type]->GetMethod("OnEnterNearArea", 3)->Call(managedObject, (EntityId)event.nParam[0], (int)event.nParam[1], (EntityId)event.nParam[2]); break; case ENTITY_EVENT_MOVENEARAREA: m_pClass[type]->GetMethod("OnMoveNearArea", 4)->Call(managedObject, (EntityId)event.nParam[0], (int)event.nParam[1], (EntityId)event.nParam[2], event.fParam[0]); break; case ENTITY_EVENT_LEAVENEARAREA: m_pClass[type]->GetMethod("OnLeaveNearArea", 3)->Call(managedObject, (EntityId)event.nParam[0], (int)event.nParam[1], (EntityId)event.nParam[2]); break; case ENTITY_EVENT_XFORM: m_pClass[type]->GetMethod("OnMove", 1)->Call(managedObject, (EEntityXFormFlags)event.nParam[0]); break; case ENTITY_EVENT_ATTACH: m_pClass[type]->GetMethod("OnAttach", 1)->Call(managedObject, (EntityId)event.nParam[0]); break; case ENTITY_EVENT_DETACH: m_pClass[type]->GetMethod("OnDetach", 1)->Call(managedObject, (EntityId)event.nParam[0]); break; case ENTITY_EVENT_DETACH_THIS: m_pClass[type]->GetMethod("OnDetachThis", 1)->Call(managedObject, (EntityId)event.nParam[0]); break; case ENTITY_EVENT_ANIM_EVENT: { const AnimEventInstance* pAnimEvent = reinterpret_cast<const AnimEventInstance*>(event.nParam[0]); ICharacterInstance* pCharacter = reinterpret_cast<ICharacterInstance*>(event.nParam[1]); IMonoClass *pAnimationEventClass = g_pScriptSystem->GetCryBraryAssembly()->GetClass("AnimationEvent"); SMonoAnimationEvent animEvent(pAnimEvent); IMonoArray *pArgs = CreateMonoArray(1); pArgs->InsertMonoObject(pAnimationEventClass->BoxObject(&animEvent)); m_pClass[type]->GetMethod("OnAnimEvent", 1)->InvokeArray(managedObject, pArgs); SAFE_RELEASE(pArgs); } break; case ENTITY_EVENT_PREPHYSICSUPDATE: { m_pClass[type]->GetMethod("OnPrePhysicsUpdate")->Invoke(managedObject); } break; } }
bool CScriptSystem::Reload() { if((!m_bFirstReload && g_pMonoCVars->mono_realtimeScripting == 0) || m_bReloading) return false; m_bReloading = true; if(!m_bFirstReload) { for each(auto listener in m_listeners) listener->OnReloadStart(); m_pScriptManager->CallMethod("Serialize"); } IMonoDomain *pScriptDomain = CreateDomain("ScriptDomain", nullptr, true); IMonoAssembly *pCryBraryAssembly = pScriptDomain->LoadAssembly(PathUtils::GetBinaryPath() + "CryBrary.dll"); IMonoArray *pCtorParams = CreateMonoArray(2); pCtorParams->InsertAny(m_bFirstReload); pCtorParams->InsertMonoString(ToMonoString(PathUtils::GetConfigPath())); IMonoObject *pScriptManager = *pCryBraryAssembly->GetClass("ScriptManager", "CryEngine.Initialization")->CreateInstance(pCtorParams); SAFE_RELEASE(pCtorParams); auto result = pScriptManager->CallMethod("Initialize", m_bFirstReload); if(result == nullptr) return false; IMonoObject *pResult = *result; auto reloadResult = pResult->Unbox<EScriptReloadResult>(); SAFE_RELEASE(pResult); switch(reloadResult) { case EScriptReloadResult_Success: { // revert previous domain if(!m_bFirstReload) m_pScriptDomain->Release(); m_pScriptDomain = pScriptDomain; m_pScriptManager = pScriptManager; m_pCryBraryAssembly = pCryBraryAssembly; CacheManagedResources(); if(!m_bFirstReload) m_pScriptManager->CallMethod("Deserialize"); // Set Network.Editor etc. IMonoClass *pClass = m_pCryBraryAssembly->GetClass("Game"); IMonoArray *pArgs = CreateMonoArray(2); pArgs->Insert(gEnv->IsEditor()); pArgs->Insert(gEnv->IsDedicated()); pClass->GetMethod("InitializeGameStatics", 2)->InvokeArray(nullptr, pArgs); SAFE_RELEASE(pArgs); m_pScriptManager->CallMethod("ProcessWaitingScripts", m_bFirstReload); for each(auto listener in m_listeners) listener->OnReloadComplete(); if(!m_bFirstReload && gEnv->IsEditor()) gEnv->pFlowSystem->ReloadAllNodeTypes(); m_bReloading = false; m_bDetectedChanges = false; return true; } break; case EScriptReloadResult_Retry: { m_bReloading = false; return Reload(); } case EScriptReloadResult_Revert: { pScriptDomain->Release(); m_pScriptDomain->SetActive(); m_bReloading = false; m_bDetectedChanges = false; return false; } break; case EScriptReloadResult_Abort: { gEnv->pSystem->Quit(); m_bReloading = false; } break; } return false; }
void CMonoFlowNode::ProcessEvent(EFlowEvent event, SActivationInfo *pActInfo) { m_pActInfo = pActInfo; if(m_pHookedGraph && m_pScript != nullptr) { m_pHookedGraph->UnregisterHook(this); m_pHookedGraph = nullptr; } switch(event) { case eFE_Activate: { IFlowNodeData *pNodeData = pActInfo->pGraph->GetNodeData(pActInfo->myID); if(!pNodeData) return; int numInputPorts = pNodeData->GetNumInputPorts(); if(m_flags & EFLN_TARGET_ENTITY) numInputPorts--; // last input is the entity port. for(int i = 0; i < numInputPorts; i++) { if(IsPortActive(i)) { switch(GetPortType(pActInfo, i)) { case eFDT_Void: m_pScript->CallMethod("OnPortActivated", i); break; case eFDT_Int: m_pScript->CallMethod("OnPortActivated", i, CFlowBaseNodeInternal::GetPortInt(pActInfo, i)); break; case eFDT_Float: m_pScript->CallMethod("OnPortActivated", i, CFlowBaseNodeInternal::GetPortFloat(pActInfo, i)); break; case eFDT_EntityId: m_pScript->CallMethod("OnPortActivated", i, CFlowBaseNodeInternal::GetPortEntityId(pActInfo, i)); break; case eFDT_Vec3: m_pScript->CallMethod("OnPortActivated", i, CFlowBaseNodeInternal::GetPortVec3(pActInfo, i)); break; case eFDT_String: m_pScript->CallMethod("OnPortActivated", i, CFlowBaseNodeInternal::GetPortString(pActInfo, i)); break; case eFDT_Bool: m_pScript->CallMethod("OnPortActivated", i, CFlowBaseNodeInternal::GetPortBool(pActInfo, i)); break; default: break; } } } } break; case eFE_Initialize: m_pScript->CallMethod("OnInit"); break; case eFE_SetEntityId: { if(pActInfo->pEntity) { IMonoArray *pParams = CreateMonoArray(2); pParams->InsertNativePointer(pActInfo->pEntity); pParams->Insert(pActInfo->pEntity->GetId()); m_pScript->GetClass()->GetMethod("InternalSetTargetEntity", 2)->InvokeArray(m_pScript->GetManagedObject(), pParams); pParams->Release(); } } break; case eFE_Update: m_pScript->CallMethod("OnNodeUpdate"); break; } }