void CCheckpointSystem::WriteVehicleData(XmlNodeRef parentNode) { IVehicleSystem *pVehicleSystem = CCryAction::GetCryAction()->GetIVehicleSystem(); IVehicleIteratorPtr pVehIt = pVehicleSystem->CreateVehicleIterator(); while(IVehicle *pVehicle = pVehIt->Next()) { SaveExternalEntity(pVehicle->GetEntityId()); } }
//------------------------------------------------------------------------ void OnDebugDrawVarChanged(ICVar* pVar) { if (pVar->GetIVal()) { IVehicleSystem* pVehicleSystem = gEnv->pGame->GetIGameFramework()->GetIVehicleSystem(); IVehicleIteratorPtr pIter = pVehicleSystem->CreateVehicleIterator(); while (IVehicle* pVehicle = pIter->Next()) { pVehicle->NeedsUpdate(); } } }
//------------------------------------------------------------------------ void CGameRules::ClientExplosion(const ExplosionInfo &explosionInfo) { // let 3D engine know about explosion (will create holes and remove vegetation) if (explosionInfo.hole_size > 1.0f && gEnv->p3DEngine->GetIVoxTerrain()) { gEnv->p3DEngine->OnExplosion(explosionInfo.pos, explosionInfo.hole_size, true); } TExplosionAffectedEntities affectedEntities; if (gEnv->bServer) { CullEntitiesInExplosion(explosionInfo); pe_explosion explosion; explosion.epicenter = explosionInfo.pos; explosion.rmin = explosionInfo.minRadius; explosion.rmax = explosionInfo.radius; if (explosion.rmax==0) explosion.rmax=0.0001f; explosion.r = explosion.rmin; explosion.impulsivePressureAtR = explosionInfo.pressure; explosion.epicenterImp = explosionInfo.pos; explosion.explDir = explosionInfo.dir; explosion.nGrow = 0; explosion.rminOcc = 0.07f; // we separate the calls to SimulateExplosion so that we can define different radii for AI and physics bodies explosion.holeSize = 0.0f; explosion.nOccRes = explosion.rmax>50.0f ? 0:16; gEnv->pPhysicalWorld->SimulateExplosion( &explosion, 0, 0, ent_living); CreateScriptExplosionInfo(m_scriptExplosionInfo, explosionInfo); UpdateAffectedEntitiesSet(affectedEntities, &explosion); // check vehicles IVehicleSystem *pVehicleSystem = g_pGame->GetIGameFramework()->GetIVehicleSystem(); uint32 vcount = pVehicleSystem->GetVehicleCount(); if (vcount > 0) { IVehicleIteratorPtr iter = g_pGame->GetIGameFramework()->GetIVehicleSystem()->CreateVehicleIterator(); while (IVehicle* pVehicle = iter->Next()) { if(IEntity *pEntity = pVehicle->GetEntity()) { AABB aabb; pEntity->GetWorldBounds(aabb); IPhysicalEntity* pEnt = pEntity->GetPhysics(); if (pEnt && aabb.GetDistanceSqr(explosionInfo.pos) <= explosionInfo.radius*explosionInfo.radius) { float affected = gEnv->pPhysicalWorld->CalculateExplosionExposure(&explosion, pEnt); AddOrUpdateAffectedEntity(affectedEntities, pEntity, affected); } } } } explosion.rmin = explosionInfo.minPhysRadius; explosion.rmax = explosionInfo.physRadius; if (explosion.rmax==0) explosion.rmax=0.0001f; explosion.r = explosion.rmin; explosion.holeSize = explosionInfo.hole_size; if (explosion.nOccRes>0) explosion.nOccRes = -1; // makes second call re-use occlusion info gEnv->pPhysicalWorld->SimulateExplosion( &explosion, 0, 0, ent_rigid|ent_sleeping_rigid|ent_independent|ent_static | ent_delayed_deformations); UpdateAffectedEntitiesSet(affectedEntities, &explosion); CommitAffectedEntitiesSet(m_scriptExplosionInfo, affectedEntities); float fSuitEnergyBeforeExplosion = 0.0f; float fHealthBeforeExplosion = 0.0f; IActor *pClientActor = g_pGame->GetIGameFramework()->GetClientActor(); if(pClientActor) { fHealthBeforeExplosion = (float)pClientActor->GetHealth(); } CallScript(m_serverStateScript, "OnExplosion", m_scriptExplosionInfo); if(pClientActor) { float fDeltaHealth = fHealthBeforeExplosion - static_cast<CPlayer *>(pClientActor)->GetHealth(); if(fDeltaHealth >= 20.0f) { SAFE_GAMEAUDIO_SOUNDMOODS_FUNC(AddSoundMood(SOUNDMOOD_EXPLOSION, MIN(fDeltaHealth, 100.0f) )); } } // call hit listeners if any if (m_hitListeners.empty() == false) { for (size_t i = 0; i < m_hitListeners.size(); ) { size_t count = m_hitListeners.size(); m_hitListeners[i]->OnServerExplosion(explosionInfo); if (count == m_hitListeners.size()) i++; else continue; } } } if (gEnv->IsClient()) { if (explosionInfo.pParticleEffect) explosionInfo.pParticleEffect->Spawn(true, IParticleEffect::ParticleLoc(explosionInfo.pos, explosionInfo.dir, explosionInfo.effect_scale)); if (!gEnv->bServer) { CreateScriptExplosionInfo(m_scriptExplosionInfo, explosionInfo); } else { affectedEntities.clear(); CommitAffectedEntitiesSet(m_scriptExplosionInfo, affectedEntities); } CallScript(m_clientStateScript, "OnExplosion", m_scriptExplosionInfo); // call hit listeners if any if (m_hitListeners.empty() == false) { THitListenerVec::iterator iter = m_hitListeners.begin(); while (iter != m_hitListeners.end()) { (*iter)->OnExplosion(explosionInfo); ++iter; } } } ProcessClientExplosionScreenFX(explosionInfo); ProcessExplosionMaterialFX(explosionInfo); if (gEnv->pAISystem && !gEnv->bMultiplayer) { // Associate event with vehicle if the shooter is in a vehicle (tank cannon shot, etc) EntityId ownerId = explosionInfo.shooterId; IActor* pActor = g_pGame->GetIGameFramework()->GetIActorSystem()->GetActor(ownerId); if (pActor && pActor->GetLinkedVehicle() && pActor->GetLinkedVehicle()->GetEntityId()) ownerId = pActor->GetLinkedVehicle()->GetEntityId(); if (ownerId != 0) { SAIStimulus stim(AISTIM_EXPLOSION, 0, ownerId, 0, explosionInfo.pos, ZERO, explosionInfo.radius); gEnv->pAISystem->RegisterStimulus(stim); SAIStimulus stimSound(AISTIM_SOUND, AISOUND_EXPLOSION, ownerId, 0, explosionInfo.pos, ZERO, explosionInfo.radius * 3.0f, AISTIMPROC_FILTER_LINK_WITH_PREVIOUS); gEnv->pAISystem->RegisterStimulus(stimSound); } } }
//------------------------------------------------------------------------ void CGameRules::ClientExplosion(const ExplosionInfo &explosionInfo) { // let 3D engine know about explosion (will create holes and remove vegetation) //if (explosionInfo.hole_size > 0.0f) //{ //gEnv->p3DEngine->OnExplosion(explosionInfo.pos, explosionInfo.hole_size, true); //} TExplosionAffectedEntities affectedEntities; if (gEnv->bServer) { CullEntitiesInExplosion(explosionInfo); pe_explosion explosion; explosion.epicenter = explosionInfo.pos; explosion.rmin = explosionInfo.minRadius; explosion.rmax = explosionInfo.radius; if (explosion.rmax==0) explosion.rmax=0.0001f; explosion.r = explosion.rmin; explosion.impulsivePressureAtR = explosionInfo.pressure; explosion.epicenterImp = explosionInfo.pos; explosion.explDir = explosionInfo.dir; explosion.nGrow = 2; explosion.rminOcc = 0.07f; // we separate the calls to SimulateExplosion so that we can define different radii for AI and physics bodies explosion.holeSize = 0.0f; explosion.nOccRes = explosion.rmax>50.0f ? 0:32; gEnv->pPhysicalWorld->SimulateExplosion( &explosion, 0, 0, ent_living); CreateScriptExplosionInfo(m_scriptExplosionInfo, explosionInfo); UpdateAffectedEntitiesSet(affectedEntities, &explosion); // check vehicles IVehicleSystem *pVehicleSystem = g_pGame->GetIGameFramework()->GetIVehicleSystem(); uint32 vcount = pVehicleSystem->GetVehicleCount(); if (vcount > 0) { IVehicleIteratorPtr iter = g_pGame->GetIGameFramework()->GetIVehicleSystem()->CreateVehicleIterator(); while (IVehicle* pVehicle = iter->Next()) { if(IEntity *pEntity = pVehicle->GetEntity()) { AABB aabb; pEntity->GetWorldBounds(aabb); IPhysicalEntity* pEnt = pEntity->GetPhysics(); if (pEnt && aabb.GetDistanceSqr(explosionInfo.pos) <= explosionInfo.radius*explosionInfo.radius) { float affected = gEnv->pPhysicalWorld->CalculateExplosionExposure(&explosion, pEnt); AddOrUpdateAffectedEntity(affectedEntities, pEntity, affected); } } } } explosion.rmin = explosionInfo.minPhysRadius; explosion.rmax = explosionInfo.physRadius; if (explosion.rmax==0) explosion.rmax=0.0001f; explosion.r = explosion.rmin; explosion.holeSize = explosionInfo.hole_size; explosion.nOccRes = -1; // makes second call re-use occlusion info gEnv->pPhysicalWorld->SimulateExplosion( &explosion, 0, 0, ent_rigid|ent_sleeping_rigid|ent_independent|ent_static ); UpdateAffectedEntitiesSet(affectedEntities, &explosion); CommitAffectedEntitiesSet(m_scriptExplosionInfo, affectedEntities); float fSuitEnergyBeforeExplosion = 0.0f; float fHealthBeforeExplosion = 0.0f; IActor *pClientActor = g_pGame->GetIGameFramework()->GetClientActor(); if(pClientActor) { fSuitEnergyBeforeExplosion = static_cast<CPlayer *>(pClientActor)->GetNanoSuit()->GetSuitEnergy(); fHealthBeforeExplosion = pClientActor->GetHealth(); } CallScript(m_serverStateScript, "OnExplosion", m_scriptExplosionInfo); if(pClientActor) { float fDeltaSuitEnergy = fSuitEnergyBeforeExplosion - static_cast<CPlayer *>(pClientActor)->GetNanoSuit()->GetSuitEnergy(); float fDeltaHealth = fHealthBeforeExplosion - pClientActor->GetHealth(); if(fDeltaSuitEnergy >= 50.0f || fDeltaHealth >= 20.0f) { SAFE_SOUNDMOODS_FUNC(AddSoundMood(SOUNDMOOD_EXPLOSION,MIN(fDeltaSuitEnergy+fDeltaHealth,100.0f))); } } // call hit listeners if any if (m_hitListeners.empty() == false) { THitListenerVec::iterator iter = m_hitListeners.begin(); while (iter != m_hitListeners.end()) { (*iter)->OnServerExplosion(explosionInfo); ++iter; } } } if (gEnv->bClient) { if (explosionInfo.pParticleEffect) explosionInfo.pParticleEffect->Spawn(true, IParticleEffect::ParticleLoc(explosionInfo.pos, explosionInfo.dir, explosionInfo.effect_scale)); if (!gEnv->bServer) { CreateScriptExplosionInfo(m_scriptExplosionInfo, explosionInfo); } else { affectedEntities.clear(); CommitAffectedEntitiesSet(m_scriptExplosionInfo, affectedEntities); } CallScript(m_clientStateScript, "OnExplosion", m_scriptExplosionInfo); // call hit listeners if any if (m_hitListeners.empty() == false) { THitListenerVec::iterator iter = m_hitListeners.begin(); while (iter != m_hitListeners.end()) { (*iter)->OnExplosion(explosionInfo); ++iter; } } } ProcessClientExplosionScreenFX(explosionInfo); ProcessExplosionMaterialFX(explosionInfo); IEntity *pShooter = m_pEntitySystem->GetEntity(explosionInfo.shooterId); if (gEnv->pAISystem && !gEnv->bMultiplayer) { IAIObject *pShooterAI(pShooter!=NULL ? pShooter->GetAI() : NULL); gEnv->pAISystem->ExplosionEvent(explosionInfo.pos,explosionInfo.radius, pShooterAI); } }
////////////////////////////////////////////////////////////////////////// //clear everything out before loading a checkpoint void CCheckpointSystem::ResetEngine() { //let game do initial resetting if (m_pGameHandler) { m_pGameHandler->OnPreResetEngine(); } //turn off physics gEnv->pSystem->SetThreadState(ESubsys_Physics, false); //reset engine similar to editor when leaving game mode //broken geometry and dynamics CCryAction::GetCryAction()->FlushBreakableObjects(); DeleteDynamicEntities(); CCryAction::GetCryAction()->ResetBrokenGameObjects(); //this should just reset the velocity of all moving things, but instead vehicle doors fall off ... //CXP : add this back in after CXP, Anton has to fix it //gEnv->pPhysicalWorld->ResetDynamicEntities(); //particle and post process effects gEnv->p3DEngine->ResetPostEffects(); gEnv->p3DEngine->ResetParticlesAndDecals(); REINST("notify the audio system?"); //AI System if (gEnv->pAISystem) { gEnv->pAISystem->Reset(IAISystem::RESET_EXIT_GAME); gEnv->pAISystem->Reset(IAISystem::RESET_ENTER_GAME); } //flow system //reset trackview gEnv->pMovieSystem->Reset(true, true); //entity system SEntityEvent event; event.event = ENTITY_EVENT_RESET; event.nParam[0] = 0; gEnv->pEntitySystem->SendEventToAll( event ); //Vehicle System IVehicleSystem *pVehicleSystem = CCryAction::GetCryAction()->GetIVehicleSystem(); IVehicleIteratorPtr pVehIt = pVehicleSystem->CreateVehicleIterator(); while(IVehicle *pVehicle = pVehIt->Next()) { pVehicle->Reset(true); } //make sure the scripts are clean gEnv->pScriptSystem->ForceGarbageCollection(); //turn on physics again gEnv->pSystem->SetThreadState(ESubsys_Physics, true); //let game do final resetting if (m_pGameHandler) { m_pGameHandler->OnPostResetEngine(); } }
void CHUDTagNames::Update() { CActor *pClientActor = static_cast<CActor *>(g_pGame->GetIGameFramework()->GetClientActor()); CGameRules *pGameRules = g_pGame->GetGameRules(); if(!pClientActor || !pGameRules || !gEnv->bMultiplayer) return; int iClientTeam = pGameRules->GetTeam(pClientActor->GetEntityId()); // Skip enemies, they need to be added only when shot // (except in spectator mode when we display everyone) for(int iTeam = 0; iTeam < pGameRules->GetTeamCount() + 1; ++iTeam) { if((iTeam == iClientTeam) || (pClientActor->GetSpectatorMode() != CActor::eASM_None)) { int iTeamPlayerCount = pGameRules->GetTeamPlayerCount(iTeam); for(int iPlayer=0; iPlayer<iTeamPlayerCount; iPlayer++) { IActor *pActor = g_pGame->GetIGameFramework()->GetIActorSystem()->GetActor(pGameRules->GetTeamPlayer(iTeam,iPlayer)); if(!pActor) continue; // Never display the local player if(pActor == pClientActor) continue; // never display other spectators if(static_cast<CActor*>(pActor)->GetSpectatorMode() != CActor::eASM_None) continue; // never display the name of the player we're spectating (it's shown separately with their current health) if(pClientActor->GetSpectatorMode() == CActor::eASM_Follow && pClientActor->GetSpectatorTarget() == pActor->GetEntityId()) continue; DrawTagName(pActor); } } } IVehicleSystem *pVehicleSystem = gEnv->pGame->GetIGameFramework()->GetIVehicleSystem(); if(!pVehicleSystem) return; IVehicleIteratorPtr pVehicleIter = pVehicleSystem->CreateVehicleIterator(); while(IVehicle *pVehicle=pVehicleIter->Next()) { SVehicleStatus rVehicleStatus = pVehicle->GetStatus(); if(0 == rVehicleStatus.passengerCount) continue; // Skip enemy vehicles, they need to be added only when shot (except in spectator mode...) bool bEnemyVehicle = true; for(int iSeatId=1; iSeatId<=pVehicle->GetLastSeatId(); iSeatId++) { IVehicleSeat *pVehicleSeat = pVehicle->GetSeatById(iSeatId); if(!pVehicleSeat) continue; EntityId uiEntityId = pVehicleSeat->GetPassenger(); if(0 == iClientTeam) { if(uiEntityId && IsFriendlyToClient(uiEntityId)) { bEnemyVehicle = false; } } else if(uiEntityId && pGameRules->GetTeam(uiEntityId) == iClientTeam) { bEnemyVehicle = false; } } if(bEnemyVehicle && (pClientActor->GetSpectatorMode() == CActor::eASM_None)) // again, draw enemies in spectator mode continue; DrawTagName(pVehicle); } // don't need to do any of this if we're in spectator mode - all player names will have been drawn above. if(pClientActor->GetSpectatorMode() == CActor::eASM_None) { for(TEnemyTagNamesList::iterator iter=m_enemyTagNamesList.begin(); iter!=m_enemyTagNamesList.end(); ++iter) { SEnemyTagName *pEnemyTagName = &(*iter); if(gEnv->pTimer->GetAsyncTime().GetSeconds() >= pEnemyTagName->fSpawnTime+((float) g_pGameCVars->hud_mpNamesDuration)) { // Note: iter=my_list.erase(iter) may not be standard/safe TEnemyTagNamesList::iterator iterNext = iter; ++iterNext; m_enemyTagNamesList.erase(iter); iter = iterNext; } else { IActor *pActor = g_pGame->GetIGameFramework()->GetIActorSystem()->GetActor(pEnemyTagName->uiEntityId); if(pActor) DrawTagName(pActor); IVehicle *pVehicle = gEnv->pGame->GetIGameFramework()->GetIVehicleSystem()->GetVehicle(pEnemyTagName->uiEntityId); if(pVehicle) DrawTagName(pVehicle); } } } }