void CPlayerStateSwim_WaterTestProxy::RayTestBottomLevel( const CPlayer& player, const Vec3& referencePosition, float maxRelevantDepth )
{
	FUNCTION_PROFILER(gEnv->pSystem, PROFILE_GAME);

	const float terrainWorldZ = gEnv->p3DEngine->GetTerrainElevation(referencePosition.x, referencePosition.y);

	int rayFlags = geom_colltype_player<<rwi_colltype_bit | rwi_stop_at_pierceable;
	int entityFlags = ent_terrain|ent_static|ent_sleeping_rigid|ent_rigid;
	const float padding = 0.2f;
	// NOTE: Terrain is above m_referencePos, so m_referencePos is probably inside a voxel or something.
	const float fPosWorldDiff = referencePosition.z - terrainWorldZ;
	float rayLength = (float)__fsel(fPosWorldDiff, min(maxRelevantDepth, fPosWorldDiff), maxRelevantDepth) + (padding * 2.0f);

	//We should not have entered this function if still waiting for the last result
	CRY_ASSERT(m_bottomLevelRayID == 0); 

	m_bottomLevelRayID = g_pGame->GetRayCaster().Queue(
		player.IsClient() ? RayCastRequest::HighPriority : RayCastRequest::MediumPriority,
		RayCastRequest(referencePosition + Vec3(0,0,padding), Vec3(0,0,-rayLength),
		entityFlags,
		rayFlags,
		0,
		0),
		functor(*this, &CPlayerStateSwim_WaterTestProxy::OnRayCastBottomLevelDataReceived));
}
void CCinematicInput::UpdateWeapons()
{
	CWeapon* pPrimaryWeapon = GetWeapon(eWeapon_Primary);
	CWeapon* pSecondaryWeapon = GetWeapon(eWeapon_Secondary);

	const bool doUpdate = (pPrimaryWeapon != NULL) || (pSecondaryWeapon != NULL);
	if (doUpdate)
	{
		const CCamera& camera = gEnv->pSystem->GetViewCamera();

		const Vec3 viewPosition  = camera.GetPosition();
		const Vec3 viewDirection = camera.GetViewdir();

		// Update raycast
		if (m_aimingRayID == 0)
		{
			IEntity *pIgnoredEntity = gEnv->pEntitySystem->GetEntity(m_weapons[eWeapon_Primary].m_parentId);
			IEntity *pIgnoredEntity2 = gEnv->pEntitySystem->GetEntity(m_weapons[eWeapon_Secondary].m_parentId);
			int ignoreCount = 0;
			IPhysicalEntity *pIgnoredEntityPhysics[2] = { NULL, NULL };
			if (pIgnoredEntity)
			{
				pIgnoredEntityPhysics[ignoreCount] = pIgnoredEntity->GetPhysics();
				ignoreCount += pIgnoredEntityPhysics[ignoreCount] ? 1 : 0;
			}
			if (pIgnoredEntity2 && (pIgnoredEntity2 != pIgnoredEntity))
			{
				pIgnoredEntityPhysics[ignoreCount] = pIgnoredEntity2->GetPhysics();
				ignoreCount += pIgnoredEntityPhysics[ignoreCount] ? 1 : 0;
			}

			m_aimingRayID = g_pGame->GetRayCaster().Queue(
				RayCastRequest::HighestPriority,
				RayCastRequest(viewPosition, viewDirection * CINEMATIC_INPUT_MAX_AIM_DISTANCE,
				ent_all|ent_water,
				rwi_stop_at_pierceable|rwi_ignore_back_faces,
				pIgnoredEntityPhysics,
				ignoreCount),
				functor(*this, &CCinematicInput::OnRayCastDataReceived));
		}

		// Update weapon orientation
		const Vec3 aimTargetPosition = viewPosition + (viewDirection * m_aimingDistance);
		if (pPrimaryWeapon != NULL)
		{
			UpdateWeaponOrientation( pPrimaryWeapon->GetEntity(), aimTargetPosition );
		}

		if (pSecondaryWeapon != NULL)
		{
			UpdateWeaponOrientation( pSecondaryWeapon->GetEntity(), aimTargetPosition );
		}
	}
}
//--------------------------------------------------------------------------------------------------
// Name: QueueMaterialEffect
// Desc: Queues material effect and sets off a deferred linetest for later processing
//--------------------------------------------------------------------------------------------------
void CExplosionGameEffect::QueueMaterialEffect(SExplosionContainer &explosionContainer)
{
	ExplosionInfo explosionInfo = explosionContainer.m_explosionInfo;

	// If an effect was already specified, don't use MFX
	if(explosionInfo.pParticleEffect)
		return;

	const int intersectionObjTypes = ent_all|ent_water;    
	const unsigned int intersectionFlags = rwi_stop_at_pierceable|rwi_colltype_any;

	CRY_ASSERT(explosionContainer.m_mfxInfo.m_rayId == 0);

	if(explosionInfo.impact)
	{
		Vec3 explosionDir = explosionInfo.impact_velocity.normalized();
		
		explosionContainer.m_mfxInfo.m_rayId = g_pGame->GetRayCaster().Queue(
			RayCastRequest::HighPriority,
			RayCastRequest(explosionInfo.pos-explosionDir*0.1f, explosionDir,
			intersectionObjTypes,
			intersectionFlags),
			functor(explosionContainer.m_mfxInfo, &SDeferredMfxExplosion::OnRayCastDataReceived));
	}
	else
	{
		const Vec3 explosionDir(0.0f, 0.0f, -g_pGameCVars->g_explosion_materialFX_raycastLength);

		explosionContainer.m_mfxInfo.m_rayId = g_pGame->GetRayCaster().Queue(
			RayCastRequest::HighPriority,
			RayCastRequest(explosionInfo.pos, explosionDir,
			intersectionObjTypes,
			intersectionFlags),
			functor(explosionContainer.m_mfxInfo, &SDeferredMfxExplosion::OnRayCastDataReceived));
	}

	explosionContainer.m_mfxInfo.m_state = eDeferredMfxExplosionState_Dispatched;
}
void StalkerModule::QueueLineOfSightRay(Agent& stalker, IAIObject* target, StalkerInstance& instance)
{
	PhysSkipList skipList;
	stalker.GetPhysicalSkipEntities(skipList);
	if (IAIActor* aiActor = target->CastToIAIActor())
		aiActor->GetPhysicalSkipEntities(skipList);

	instance.rayID = g_pGame->GetRayCaster().Queue(
		RayCastRequest::HighPriority,
		RayCastRequest(target->GetPos(), stalker.GetPos() - target->GetPos(),
		ent_terrain|ent_static|ent_rigid|ent_sleeping_rigid,
		((geom_colltype_ray << rwi_colltype_bit) | rwi_colltype_any | (10 & rwi_pierceability_mask)),
		&skipList[0], skipList.size()),
		functor(*this, &StalkerModule::LineOfSightRayComplete));
}
Exemple #5
0
const Vec3& CPlayerRotation::SLeanAndPeekInfo::GetLeanLimit( const Vec3 &startPos, const Vec3 &dir, int objTypes, int flags, IPhysicalEntity **pSkipEnts /*= NULL*/, int nSkipEnts /*= 0*/ )
{
	//Only queue ray cast if not waiting for another one
	if (m_queuedRayID == 0)
	{
		m_queuedRayID = g_pGame->GetRayCaster().Queue(
			RayCastRequest::MediumPriority,
			RayCastRequest(startPos, dir,
			objTypes,
			flags,
			pSkipEnts,
			nSkipEnts),
			functor(*this, &SLeanAndPeekInfo::OnRayCastDataReceived));
	}

	return m_lastLimit;
}
Exemple #6
0
    void CWeaponCheck::CastRays()
    {
      IActor* pActor = gEnv->pGame->GetIGameFramework()->GetClientActor();
      CPlayer* pPlayer = pActor ? static_cast<CPlayer*>(pActor) : NULL;
      if( !pPlayer ) {
        m_closestDist = 10000.f;
        return;
      }

      m_closestDist = m_closestCastDist;
      m_closestCastDist = 10000.f;
      m_numFramesWaiting = m_numResults = 0;

      const CCamera& camera = gEnv->pRenderer->GetCamera();
      Vec3 camPos = camera.GetPosition();
      Ang3 angles = camera.GetAngles();
      Vec3 rayDirs[Stereo3D::Weapon::MAX_RAY_IDS] = {
        gEnv->pRenderer->GetCamera().GetViewdir(),
        Quat::CreateRotationXYZ(Ang3(angles.y - camera.GetFov() * 0.25f,angles.z - camera.GetHorizontalFov() * 0.25f,angles.x)).GetColumn1(),
        Quat::CreateRotationXYZ(Ang3(angles.y,angles.z + camera.GetHorizontalFov() * 0.25f,angles.x)).GetColumn1(),
        Quat::CreateRotationXYZ(Ang3(angles.y,angles.z - camera.GetHorizontalFov() * 0.25f,angles.x)).GetColumn1(),
        Quat::CreateRotationXYZ(Ang3(angles.y - camera.GetFov() * 0.25f,angles.z + camera.GetHorizontalFov() * 0.25f,angles.x)).GetColumn1(),
      };
      IPhysicalEntity *pTargetPhysics = pPlayer->GetEntity()->GetPhysics();
      for ( int i = 0; i < Stereo3D::Weapon::MAX_RAY_IDS; ++i )
      {
        if ( m_rayIDs[i] != Stereo3D::Weapon::INVALID_RAY_ID )
        {
          g_pGame->GetRayCaster().Cancel(m_rayIDs[i]);
        }

        m_rayIDs[i] =
          g_pGame->GetRayCaster().Queue(RayCastRequest::MediumPriority,
          RayCastRequest(camPos, rayDirs[i] * 3,
          ent_all, rwi_stop_at_pierceable|rwi_ignore_back_faces,
          pTargetPhysics ? &pTargetPhysics : 0,
          pTargetPhysics ? 1 : 0),
          functor(*this, &CWeaponCheck::OnRayCastResult));
      }
    }
void CDeferredExplosionEffect::RequestRayCast( CDeferredExplosionEffect::EDeferredEffectType effectType, const Vec3 &startPos, const Vec3 &dir, float distance, float effectMaxDistance, int objTypes, int flags, IPhysicalEntity **pSkipEnts, int nSkipEnts )
{
	FreeOldestRequestIfNeeded();

	SQueuedRayInfo requestedRay;
	requestedRay.effectType = effectType;
	requestedRay.effectMaxDistance = effectMaxDistance;
	requestedRay.distance = distance;
	requestedRay.explosionPos = startPos;
	requestedRay.request = ++m_requestCounter;

	requestedRay.rayID = g_pGame->GetRayCaster().Queue(
		RayCastRequest::HighPriority,
		RayCastRequest(startPos, dir * distance,
		objTypes,
		flags,
		pSkipEnts,
		nSkipEnts),
		functor(*this, &CDeferredExplosionEffect::OnRayCastDataReceived));

	m_queuedRays.push_back(requestedRay);
}
void CLaserBeam::UpdateLaser(const CLaserBeam::SLaserUpdateDesc& laserUpdateDesc)
{
	if(m_pLaserParams && m_laserOn)
	{
		IEntity* pLaserEntity = CreateLaserEntity();
		if (pLaserEntity)
		{
			m_lastLaserUpdatePosition = laserUpdateDesc.m_laserPos;
			m_lastLaserUpdateDirection = laserUpdateDesc.m_laserDir;

			m_laserUpdateTimer += laserUpdateDesc.m_frameTime;

			UpdateLaserGeometry(*pLaserEntity);

			if(m_laserUpdateTimer < LASER_UPDATE_TIME)
				return;

			m_laserUpdateTimer = Random(0.0f, LASER_UPDATE_TIME * 0.4f);

			if ((laserUpdateDesc.m_ownerCloaked && !laserUpdateDesc.m_weaponZoomed) || laserUpdateDesc.m_bOwnerHidden)
			{
				pLaserEntity->Hide(true);
				return;
			}
			pLaserEntity->Hide(false);

			const float range = m_pLaserParams->laser_range[GetIndexFromGeometrySlot()];

			// Use the same flags as the AI system uses for visbility.
			const int objects = ent_terrain|ent_static|ent_rigid|ent_sleeping_rigid|ent_independent; //ent_living;
			const int flags = (geom_colltype_ray << rwi_colltype_bit) | rwi_colltype_any | (10 & rwi_pierceability_mask) | (geom_colltype14 << rwi_colltype_bit);

			//If we did not get a result, just cancel it, we will queue a new one again
			RayCastRequest::Priority requestPriority = RayCastRequest::MediumPriority;
			if (m_queuedRayId != 0)
			{
				g_pGame->GetRayCaster().Cancel(m_queuedRayId);
				m_queuedRayId = 0;
				requestPriority = RayCastRequest::HighPriority;
			}

			IItemSystem* pItemSystem = g_pGame->GetIGameFramework()->GetIItemSystem();
			IPhysicalEntity* pSkipEntity = NULL;
			uint8 numSkips = 0;

			CItem* pItem = static_cast<CItem*>(pItemSystem->GetItem(m_ownerEntityId));

			if(pItem)
			{
				if(pItem->IsAccessory())
				{
					CItem* pParentItem = static_cast<CItem*>(pItemSystem->GetItem(pItem->GetParentId()));
				
					if(pParentItem)
					{
						pItem = pParentItem;
					}					
				}

				IEntity* pOwnerEnt = 0;
				CWeapon* pWeapon = static_cast<CWeapon*>(pItem->GetIWeapon());
				if (pWeapon && pWeapon->GetHostId() != 0)
				{
					pOwnerEnt = gEnv->pEntitySystem->GetEntity(pWeapon->GetHostId());
				}
				else
				{
					pOwnerEnt = pItem->GetOwner();
				}

				if(pOwnerEnt)
				{
					IPhysicalEntity* pOwnerPhysics = pOwnerEnt->GetPhysics();

					if(pOwnerPhysics)
					{
						pSkipEntity = pOwnerPhysics;
						numSkips++;
					}
				}
			}

			m_queuedRayId = g_pGame->GetRayCaster().Queue(
				requestPriority,
				RayCastRequest(laserUpdateDesc.m_laserPos, laserUpdateDesc.m_laserDir*range,
				objects,
				flags,
				&pSkipEntity,
				numSkips),
				functor(*this, &CLaserBeam::OnRayCastDataReceived));
		}

	}
	else if (!m_pLaserParams)
	{
		GameWarning("LASER PARAMS: Item of type CLaser is missing it's laser params!");
	}
}
QueuedRayID CCameraRayScan::ShootRay(const Vec3 &rayPos, const Vec3 &rayDir, int objTypes /*= g_objTypes*/, int geomFlags /*= g_geomFlags*/, IPhysicalEntity **pSkipEnts /*= NULL*/, int numSkipEnts /*= 0*/)
{
	return g_pGame->GetRayCaster().Queue(RayCastRequest::MediumPriority,
										 RayCastRequest(rayPos, rayDir, objTypes, geomFlags, pSkipEnts, numSkipEnts),
										 functor(*this, &CCameraRayScan::OnRayCastResult));
}
void CPlayerVisTable::DoVisibilityCheck(const Vec3& localPlayerPosn, SVisTableEntry& visInfo, VisEntryIndex visIndex)
{
	Vec3 vecToTarget;

	IEntity * pEntity = gEnv->pEntitySystem->GetEntity(visInfo.entityId);

	if(pEntity)
	{
		IPhysicalEntity* pTargetPhysEnt = pEntity->GetPhysics();

		SDeferredLinetestBuffer& targetBuffer = m_linetestBuffers[GetCurrentLinetestBufferTargetIndex()];

		if(targetBuffer.m_numLinetestsCurrentlyProcessing < kMaxVisTableLinetestsPerFrame)
		{
			visInfo.framesSinceLastCheck = 0;

			SDeferredLinetestReceiver * processingEntry = GetAvailableDeferredLinetestReceiver(targetBuffer);

			assert(processingEntry);

			Vec3 targetPosn = pEntity->GetWorldPos();
			if (visInfo.flags & eVF_CheckAgainstCenter)
			{
				AABB targetBbox;
				pEntity->GetWorldBounds(targetBbox);
				if (!targetBbox.IsEmpty())
				{
					targetPosn = targetBbox.GetCenter();
				}
				float radius = min(min(targetBbox.max.x-targetBbox.min.x, targetBbox.max.y-targetBbox.min.y), targetBbox.max.z-targetBbox.min.z);
				targetPosn += (localPlayerPosn-targetPosn).GetNormalized() * radius * 0.25f;
			}
			targetPosn.z += visInfo.heightOffset;
			vecToTarget = targetPosn - localPlayerPosn;

			processingEntry->visTableIndex = visIndex;			

			ray_hit hit;
			const int rayFlags = rwi_colltype_any(geom_colltype_solid&(~geom_colltype_player)) | rwi_ignore_noncolliding | rwi_pierceability(PIERCE_GLASS);

			m_numLinetestsThisFrame++;
			targetBuffer.m_numLinetestsCurrentlyProcessing++;

			visInfo.flags |= eVF_Pending;
			visInfo.flags &= ~eVF_CheckAgainstCenter;

			processingEntry->visBufferIndex = m_currentBufferTarget;

			const int numEntries = kMaxNumIgnoreEntities + 1; 
			IPhysicalEntity* pSkipEnts[numEntries];
			int numSkipEnts = 0;

			if(pTargetPhysEnt)
			{
				pSkipEnts[numSkipEnts] = pTargetPhysEnt;
				numSkipEnts++;
			}
			if (m_currentNumIgnoreEntities)
			{
				for(int i = 0; i < m_currentNumIgnoreEntities; ++i)
				{
					SIgnoreEntity& ignoreEnt = m_globalIgnoreEntities[i];
					CRY_ASSERT(ignoreEnt.id); 

					IEntity* pIgnoreEntity = gEnv->pEntitySystem->GetEntity(ignoreEnt.id);
					IPhysicalEntity* pIgnorePhysicsEntity = pIgnoreEntity ? pIgnoreEntity->GetPhysics() : NULL;

					if (pIgnorePhysicsEntity)
					{
						pSkipEnts[numSkipEnts] = pIgnorePhysicsEntity;
						numSkipEnts++;
					}
				}
			}
			
			CRY_ASSERT(processingEntry->queuedRayID == 0);

			processingEntry->queuedRayID = g_pGame->GetRayCaster().Queue(
				RayCastRequest::HighPriority,
				RayCastRequest(localPlayerPosn, vecToTarget,
				ent_terrain|ent_static|ent_sleeping_rigid|ent_rigid,
				rayFlags,
				pSkipEnts,
				numSkipEnts, 2),
				functor(*processingEntry, &SDeferredLinetestReceiver::OnDataReceived));

#if ALLOW_VISTABLE_DEBUGGING
			m_debugDraw.UpdateDebugTarget(visInfo.entityId, targetPosn, ((visInfo.flags & eVF_Visible) != 0));
#endif

		}
	}
	else
	{
		visInfo.flags |= eVF_Remove;
	}
}