Example #1
0
void CCameraFlight::DetectCollisions()
{
	primitives::sphere	sph;
	sph.r				= 0.15f;
	sph.center	= m_vTargetFadePos + m_vLookingDirection * RAY_SCAN_DISTANCE;
	CCameraRayScan *pRayScan = g_pGame->GetCameraManager()->GetCamView()->GetCamRayScan();
	if (m_RayId == INVALID_RAY_ID)
	{
		m_RayId = pRayScan->ShootRay(sph.center, -m_vLookingDirection * RAY_SCAN_DISTANCE, ent_all & ~(ent_living | ent_independent | ent_rigid), geom_colltype0);
	}
	const RayCastResult* pRayRes = pRayScan->GetExternalHit(m_RayId);
	const ray_hit *pHit = pRayRes->hitCount > 0 ? &pRayRes->hits[0] : NULL;
	static int iNumHits = 0;
	if(pHit && pHit->dist > 0.0f)
	{
		iNumHits++;
		if(iNumHits > 2)
		{
			bool bIgnore = false;
			IPhysicalEntity *pPhysEntity = pHit->pCollider;
			if(pPhysEntity)
			{
				int iForeignData = pPhysEntity->GetiForeignData();
				if (iForeignData == PHYS_FOREIGN_ID_STATIC)
				{
					//check whether the hit rendernode is "vegetation"
					void *pForeignData = pPhysEntity->GetForeignData(PHYS_FOREIGN_ID_STATIC);
					IRenderNode * pRN = (IRenderNode*)pForeignData;
					if(pRN && pRN->GetRenderNodeType() == eERType_Vegetation)
						bIgnore = true;
				}
				else if(iForeignData == PHYS_FOREIGN_ID_ENTITY)
				{
					IEntity *pEntity = gEnv->pEntitySystem->GetEntityFromPhysics(pPhysEntity);
					if(pEntity && (pEntity == m_pRefEnt || pEntity->GetId() == LOCAL_PLAYER_ENTITY_ID))
						bIgnore = true;
				}
				else if(iForeignData == -1)
					bIgnore = true;
			}

			if(!bIgnore)
				m_vTargetFadePos = m_vTargetFadePos + m_vLookingDirection * max(0.0f, (RAY_SCAN_DISTANCE - pHit->dist));
			else
				iNumHits = 0;
		}
	}
	else
		iNumHits = 0;

	if (pRayRes)
	{
		pRayScan->RemoveExternalHit(m_RayId);
		m_RayId = INVALID_RAY_ID;
	}
}
Example #2
0
//------------------------------------------------------------------------
IEntity *CWorkOnTarget::CanWork()
{
	static Vec3 pos,dir; 
	static ICVar* pAimDebug = gEnv->pConsole->GetCVar("g_aimdebug");
	
	CActor *pActor=m_pWeapon->GetOwnerActor();
	
	static IPhysicalEntity* pSkipEntities[10];
	int nSkip = CSingle::GetSkipEntities(m_pWeapon, pSkipEntities, 10);

	IEntity *pEntity=0;
	float range=m_workparams.range;
	
	IMovementController * pMC = pActor ? pActor->GetMovementController() : 0;
	if (pMC)
	{ 
		SMovementState info;
		pMC->GetMovementState(info);

		pos = info.weaponPosition;

		if (!pActor->IsPlayer())
		{
			dir = range * (info.fireTarget-pos).normalized();
		}
		else
		{
			dir = range * info.fireDirection;    

			// marcok: leave this alone
			if (g_pGameCVars->goc_enable && pActor->IsClient())
			{
				CPlayer *pPlayer = (CPlayer*)pActor;
				pos = pPlayer->GetViewMatrix().GetTranslation();
			}
		}
	}
	else
	{ 
		assert(0);
	}

	primitives::sphere sphere;
	sphere.center = pos;
	sphere.r = m_workparams.radius;
	Vec3 end = pos+dir;

	geom_contact *pContact=0;
	float dst=gEnv->pPhysicalWorld->PrimitiveWorldIntersection(sphere.type, &sphere, end-sphere.center, ent_all,
		&pContact, 0, (geom_colltype_player<<rwi_colltype_bit)|rwi_stop_at_pierceable, 0, 0, 0, pSkipEntities, nSkip);

	if (pContact && dst>=0.0f)
	{
		IPhysicalEntity *pCollider = gEnv->pPhysicalWorld->GetPhysicalEntityById(pContact->iPrim[0]);

		if(pCollider && pCollider->GetiForeignData() == PHYS_FOREIGN_ID_ENTITY)
		{
			if (pEntity = static_cast<IEntity *>(pCollider->GetForeignData(PHYS_FOREIGN_ID_ENTITY)))
			{
				if (CGameRules *pGameRules=g_pGame->GetGameRules())
				{
					if (IScriptTable *pScriptTable=pGameRules->GetEntity()->GetScriptTable())
					{
						HSCRIPTFUNCTION pfnCanWork=0;
						if (pScriptTable->GetValueType("CanWork")==svtFunction && pScriptTable->GetValue("CanWork", pfnCanWork))
						{
							bool result=false;
							Script::CallReturn(gEnv->pScriptSystem, pfnCanWork, pScriptTable, ScriptHandle(pEntity->GetId()), ScriptHandle(m_pWeapon->GetOwnerId()), m_workparams.work_type.c_str(), result);
							gEnv->pScriptSystem->ReleaseFunc(pfnCanWork);

							if (result)
								return pEntity;
						}
					}
				}
			}
		}
	}

	return 0;
}