예제 #1
0
void CBotNav::Update()
{
   RecordWaterState(); // record if bot needs to find air

   // if bot is supposed to move, record if bot is stuck
   if (m_pBot->GetMaxspeed() > 10 &&
      (m_pBot->bi.actionflags & (ACTION_MOVEFORWARD | ACTION_MOVEBACK | ACTION_MOVELEFT | ACTION_MOVERIGHT))) {
      // is it the time to check if bot is stuck?
      if (FZero(m_flStuckCheckTime)) {
         // first time, just record bot's current location
         m_flStuckCheckTime = g_pServer->GetTime() + 2;
         m_vecPrevLocation = m_pBot->GetOrigin();
         m_flIsStuck = 0;
      } else if (m_flStuckCheckTime < g_pServer->GetTime()) {
         m_flStuckCheckTime = g_pServer->GetTime() + 0.5; // next stuck checking time

         // if bot is on ground, check 2D Vector only; else check 3D Vector
         float flBotMoved;
         if (m_pBot->IsOnFloor()) {
            flBotMoved = (m_vecPrevLocation - m_pBot->GetOrigin()).LengthSquared2D();
         } else {
            flBotMoved = (m_vecPrevLocation - m_pBot->GetOrigin()).LengthSquared();
         }

         // Did we NOT move enough previously?
         if (flBotMoved < SQUARE(2)) {
            m_flIsStuck += 0.3; // consider being stuck if so
         } else if (m_pBot->IsOnFloor()) {
            m_flIsStuck -= 0.2 * m_pBot->GetSpeed2D() / m_pBot->GetMaxspeed();
         } else {
            m_flIsStuck -= 0.2 * m_pBot->GetSpeed() / m_pBot->GetMaxspeed();
         }

         if (m_flIsStuck > 1.0)
            m_flIsStuck = 1.0;
         else if (m_flIsStuck < 0)
            m_flIsStuck = 0;

         m_vecPrevLocation = m_pBot->GetOrigin(); // record bot's current location

         if (m_fPrevIsStuck && !IsStuck()) {
            m_pBot->DebugMsg(DEBUG_BOTNAV, "Bot is UNSTUCK");
         } else if (!m_fPrevIsStuck && IsStuck()) {
            m_pBot->DebugMsg(DEBUG_BOTNAV, "Bot is STUCK!!!");
         }

         m_fPrevIsStuck = IsStuck();
      }
   } else {
      // bot is supposed not to move
      m_vecPrevLocation = NULLVEC;
      m_flStuckCheckTime = 0;
      m_flIsStuck = 0;
   }
}
bool CStickyProjectile::IsValid() const
{
	if (!IsStuck())
		return false;

	if(m_parentId == 0)
		return true;

	pe_params_part part;
	part.partid = m_stuckPartId;
	IEntity* pEntity = gEnv->pEntitySystem->GetEntity(m_parentId);
	if(pEntity)
	{
		if (pEntity->IsHidden())
		{
			return false;
		}
		if(ICharacterInstance* pCharacter = pEntity->GetCharacter(0))
		{
			if(ISkeletonPose* pSkel = pCharacter->GetISkeletonPose())
			{
				IPhysicalEntity* pSkelPhysics = pSkel->GetCharacterPhysics();
				if (pSkelPhysics)
				{
					return pSkelPhysics->GetParams(&part) != 0;
				}
			}
		}
		else
		{
			IPhysicalEntity* pPhysics = pEntity->GetPhysics();
			if (pPhysics)
			{
				return pPhysics->GetParams(&part) != 0;
			}
		}
	}

	return false;
}