示例#1
0
文件: Alarm.cpp 项目: emoose/lithtech
void Alarm::CreateRegionList(HSTRING& hstrRegions, AIREGION_LIST* pList)
{
	// Create a list of regions.
	// Named object may be a region, a list of regions separated by semicolons.

	if( hstrRegions )
	{
		char szRegions[REGION_STRING_LEN + 1];		
		
		const char* pszRegions = g_pLTServer->GetStringData( hstrRegions );
		AIASSERT( strlen( pszRegions ) <= REGION_STRING_LEN, m_hObject, "Alarm::CreateRegionList: RegionList is longer than 256 chars." );
		strncpy( szRegions, pszRegions, REGION_STRING_LEN );
		
		char* tok = strtok( szRegions, "; " );
		while( tok )
		{
			HOBJECT hObject;
			if( ( LT_OK == FindNamedObject( tok, hObject ) ) &&
				( IsAIRegion( hObject ) ) )
			{
				pList->push_back( hObject );
			}
			else {
				char szError[128];
				sprintf( szError, "Alarm::CreateRegionList: '%s' is not a region.", tok ); 
				AIASSERT( 0, m_hObject, szError );
			}

			tok = strtok( LTNULL, "; " );
		}
	}

	FREE_HSTRING( hstrRegions );
}
示例#2
0
void CNamedObjectList::InitNamedObjectList( HOBJECT hOwner )
{
	m_hObject = hOwner;

	// Reserve space for handles.

	m_lstObjectHandles.reserve( m_lstObjectNames.size() );

	// Find named objects.

	HOBJECT hObject = NULL;
	StringArray::iterator str_it;
	for ( str_it = m_lstObjectNames.begin(); str_it != m_lstObjectNames.end(); ++str_it )
	{
		if( LT_OK != FindNamedObject( str_it->c_str(), hObject, false ) )
		{
			LTASSERT_PARAM1( 0, "CNamedObjectList::InitNamedObjectList: Cannot find named object \"%s\"", str_it->c_str() );
			hObject = NULL;
		}

		// Add handle to the list.

		m_lstObjectHandles.push_back( hObject );
	}
}
示例#3
0
void CAIHelicopterStateAttack::HandleNameValuePair(char *szName, char *szValue)
{
	CAIHelicopterState::HandleNameValuePair(szName, szValue);

	if ( !_stricmp(szName, "FIRE") )
	{
		if ( !_stricmp(szValue, "FULL") )
		{
			m_pStrategyShoot->SetFire(CAnimatorAIVehicle::eFireFull);
		}
		else if ( !_stricmp(szValue, "FIRE1") )
		{
			m_pStrategyShoot->SetFire(CAnimatorAIVehicle::eFire1);
		}
		else if ( !_stricmp(szValue, "FIRE2") )
		{
			m_pStrategyShoot->SetFire(CAnimatorAIVehicle::eFire2);
		}
		else if ( !_stricmp(szValue, "FIRE3") )
		{
			m_pStrategyShoot->SetFire(CAnimatorAIVehicle::eFire3);
		}
		else if ( !_stricmp(szValue, "FIRE4") )
		{
			m_pStrategyShoot->SetFire(CAnimatorAIVehicle::eFire4);
		}
		else
		{
            g_pLTServer->CPrint("CAIHelicopterStateAttack - FIRE=%s is not a valid fire type", szValue);
		}
	}
	else if ( !_stricmp(szName, "TARGET") )
	{
		GetAI()->Unlink(m_hTarget);
		m_hTarget = LTNULL;

		if ( LT_OK == FindNamedObject(szValue, m_hTarget) )
		{
			if ( IsKindOf(m_hTarget, "CCharacter") )
			{
				GetAI()->Link(m_hTarget);
			}
			else
			{
                g_pLTServer->CPrint("ATTACK TARGET=%s -- this object is not a CCharacter!", szValue);
				m_hTarget = LTNULL;
			}
		}
		else
		{
            g_pLTServer->CPrint("ATTACK TARGET=%s -- this object does not exist!", szName);
		}
	}
}
LTBOOL CAIGoalAbstractTargeted::HandleNameValuePair(const char *szName, const char *szValue)
{
	ASSERT(szName && szValue);

	if ( !_stricmp(szName, "TARGET") )
	{
		HOBJECT hObj = m_hTarget;
		FindNamedObject(szValue, hObj);
		m_hTarget = hObj;
		return LTTRUE;
	}

	return LTFALSE;
}
示例#5
0
void Camera::HandleMoveToMsg(	HOBJECT hSender, const CParsedMsg &crParsedMsg )
{
	HOBJECT hObject;
	if( LT_OK == FindNamedObject( crParsedMsg.GetArg(1), hObject ))
	{
		if( !IsKindOf( hObject, "CameraPoint" ))
			return;

		// Just place the camera at the Point's position and rotation...

		LTRigidTransform tTrans;
		g_pLTServer->GetObjectTransform(hObject, &tTrans);
		g_pLTServer->SetObjectTransform(m_hObject, tTrans);
	}
}
示例#6
0
文件: AICmd.cpp 项目: Arc0re/lithtech
void AICmdTalk::Verify()
{
	super::Verify();

	HOBJECT hObject;
	if ( !!m_hstrFace && LT_OK != FindNamedObject(g_pLTServer->GetStringData(m_hstrFace), hObject) )
	{
		Warn("AICmd \"%s\" - Could not find face \"%s\"", ::ToString(m_hstrName), ::ToString(m_hstrFace));
	}

	if ( m_fFaceTime < 0.0f )
	{
		Warn("AICmd \"%s\" - FaceTime is less than 0.0", ::ToString(m_hstrName));
	}
}
示例#7
0
文件: AICmd.cpp 项目: Arc0re/lithtech
void AICmdCheckBody::Verify()
{
	super::Verify();

	if ( !!m_hstrBody )
	{
		HOBJECT hObject;
		if ( LT_OK != FindNamedObject(g_pLTServer->GetStringData(m_hstrBody), hObject) )
		{
			Warn("AICmd \"%s\" - Could not find body \"%s\"", ::ToString(m_hstrName), ::ToString(m_hstrBody));
		}
	}
	else
	{
		Warn("AICmd \"%s\" - No body specified", ::ToString(m_hstrName));
	}
}
示例#8
0
文件: AICmd.cpp 项目: Arc0re/lithtech
void AICmdAttackProp::Verify()
{
	super::Verify();

	if ( !!m_hstrProp )
	{
		HOBJECT hObject;
		if ( LT_OK != FindNamedObject(g_pLTServer->GetStringData(m_hstrProp), hObject) )
		{
			Warn("AICmd \"%s\" - Could not find prop \"%s\"", ::ToString(m_hstrName), ::ToString(m_hstrProp));
		}
	}
	else
	{
		Warn("AICmd \"%s\" - No prop specified", ::ToString(m_hstrName));
	}
}
示例#9
0
文件: AICmd.cpp 项目: Arc0re/lithtech
void AICmdFlee::Verify()
{
	super::Verify();

	if ( !!m_hstrDanger )
	{
		HOBJECT hObject;
		if ( LT_OK != FindNamedObject(g_pLTServer->GetStringData(m_hstrDanger), hObject) )
		{
			Warn("AICmd \"%s\" - Could not find danger \"%s\"", ::ToString(m_hstrName), ::ToString(m_hstrDanger));
		}
	}
	else
	{
		Warn("AICmd \"%s\" - No danger specified", ::ToString(m_hstrName));
	}
}
示例#10
0
void CAIGoalAttackProp::SetStateAttack()
{
	m_pAI->SetCurrentWeapon( m_eWeaponType );

	if( m_pAI->GetState()->GetStateType() != kState_HumanAttackProp )
	{
		m_pAI->SetState( kState_HumanAttackProp );

		// Set object to attack.

		HOBJECT hObject;
		AINode* pNode = (AINode*)g_pLTServer->HandleToObject(m_hNode);
		CAIHumanStateAttackProp* pStateAttackProp = (CAIHumanStateAttackProp*)(m_pAI->GetState());
		if ( LT_OK == FindNamedObject(pNode->GetObject(), hObject) )
		{
			pStateAttackProp->SetProp(hObject);
		}
	}
}
示例#11
0
AINode* CAIGoalAttackProp::HandleGoalAttractors()
{
	// Check if already attacking a prop.
	if( m_pAI->GetState()->GetStateType() != kState_HumanAttackProp )
	{
		CAIHuman* pAIHuman = (CAIHuman*)m_pAI;
		if( pAIHuman->HasHolsterString() || pAIHuman->GetPrimaryWeapon())
		{
			AIGBM_GoalTemplate* pTemplate = g_pAIGoalButeMgr->GetTemplate( GetGoalType() );
			AIASSERT(pTemplate->cAttractors > 0, m_pAI->m_hObject, "CAIGoalAbstract::HandleGoalAttractors: Goal has no attractors.");

			// Check if attractors are triggering activateability.
			AINode* pNode;
			for(uint32 iAttractor=0; iAttractor < pTemplate->cAttractors; ++iAttractor)
			{
				pNode = g_pAINodeMgr->FindNearestNodeInRadius(m_pAI, pTemplate->aAttractors[iAttractor], m_pAI->GetPosition(), pTemplate->fAttractorDistSqr * m_fBaseImportance, LTTRUE);
				if(pNode != LTNULL)
				{
					HOBJECT hObject;
					if ( LT_OK == FindNamedObject(pNode->GetObject(), hObject) )
					{
						Prop* pProp = (Prop*)g_pLTServer->HandleToObject(hObject);
						if(pProp->GetState() != kState_PropDestroyed)
						{
							AIASSERT(pNode->GetType() == kNode_UseObject, m_pAI->m_hObject, "CAIGoalAttackProp::HandleGoalAttractors: AINode is not of type UseObject.");
							m_hNode = pNode->m_hObject;
							SetCurToBaseImportance();
							return pNode;
						}
					}
					
					// Disable node if prop has been destroyed.
					pNode->Disable();				
				}
			}
		}

		m_hNode = LTNULL;
	}
	return LTNULL;
}
示例#12
0
void GameBase::HandleCopyXFormMsg( HOBJECT hSender, const CParsedMsg &crParsedMsg )
{
	// Make sure we have all the arguments.
	if( crParsedMsg.GetArgCount( ) < 2 )
		return;

	// Get the target object.
	HOBJECT hTarget = NULL;
	FindNamedObject( crParsedMsg.GetArg( 1 ), hTarget, false );
	if( !hTarget )
		return;

	// Set the position for this object.
	LTVector vPos;
	g_pLTServer->GetObjectPos( hTarget, &vPos );
	g_pLTServer->SetObjectPos( m_hObject, vPos );

	// Set the rotation for this object.
	LTRotation rRot;
	g_pLTServer->GetObjectRotation( hTarget, &rRot );
	g_pLTServer->SetObjectRotation( m_hObject, rRot );
}
示例#13
0
文件: AICmd.cpp 项目: Arc0re/lithtech
void AICmdInvestigate::Verify()
{
	super::Verify();

	if ( LT_INSIDE != g_pLTServer->Common()->GetPointStatus(&m_vPosition) )
	{
		Warn("AICmd \"%s\" - Position %s is not in the world", ::ToString(m_hstrName), ::ToString(m_vPosition));
	}

	if ( !!m_hstrEnemy )
	{
		HOBJECT hObject;
		if ( LT_OK != FindNamedObject(g_pLTServer->GetStringData(m_hstrEnemy), hObject) )
		{
			Warn("AICmd \"%s\" - Could not find enemy \"%s\"", ::ToString(m_hstrName), ::ToString(m_hstrEnemy));
		}
	}
	else
	{
		Warn("AICmd \"%s\" - No enemy specified", ::ToString(m_hstrName));
	}

}
示例#14
0
void AINodeValidatorBoundaryRadius::InitNodeValidator( AINode* pNode )
{
	// Sanity check.

	if( !pNode )
	{
		return;
	}

	// Find AIRegion by name, and record it's AIRegionID.

	if( !m_strBoundaryAIRegion.empty() )
	{
		ILTBaseClass *pObject = NULL;
		if( LT_OK == FindNamedObject( m_strBoundaryAIRegion.c_str(), pObject ) )
		{
			AIRegion* pAIRegion = (AIRegion*)pObject;
			if( pAIRegion )
			{
				m_eBoundaryAIRegion = pAIRegion->GetAIRegionID();
			}
		}
	}
}
Maybe<bool>
Compatibility::OnUIAMessage(WPARAM aWParam, LPARAM aLParam)
{
  auto clearUiaRemotePid = MakeScopeExit([]() {
    sUiaRemotePid = Nothing();
  });

  Telemetry::AutoTimer<Telemetry::A11Y_UIA_DETECTION_TIMING_MS> timer;

  // UIA creates a section containing the substring "HOOK_SHMEM_"
  NS_NAMED_LITERAL_STRING(kStrHookShmem, "HOOK_SHMEM_");

  // The section name always ends with this suffix, which is derived from the
  // current thread id and the UIA message's WPARAM and LPARAM.
  nsAutoString partialSectionSuffix;
  partialSectionSuffix.AppendPrintf("_%08x_%08x_%08x", ::GetCurrentThreadId(),
                                    static_cast<DWORD>(aLParam), aWParam);

  // Find any named Section that matches the naming convention of the UIA shared
  // memory.
  nsAutoHandle section;
  auto comparator = [&](const nsDependentSubstring& aName,
                        const nsDependentSubstring& aType) -> bool {
    if (aType.Equals(NS_LITERAL_STRING("Section")) &&
        FindInReadable(kStrHookShmem, aName) &&
        StringEndsWith(aName, partialSectionSuffix)) {
      section.own(::OpenFileMapping(GENERIC_READ, FALSE,
                                    PromiseFlatString(aName).get()));
      return false;
    }

    return true;
  };

  if (!FindNamedObject(comparator) || !section) {
    return Nothing();
  }

  NTSTATUS ntStatus;

  // First we must query for a list of all the open handles in the system.
  UniquePtr<char[]> handleInfoBuf;
  ULONG handleInfoBufLen = sizeof(SYSTEM_HANDLE_INFORMATION_EX) +
                           1024 * sizeof(SYSTEM_HANDLE_TABLE_ENTRY_INFO_EX);

  // We must query for handle information in a loop, since we are effectively
  // asking the kernel to take a snapshot of all the handles on the system;
  // the size of the required buffer may fluctuate between successive calls.
  while (true) {
    // These allocations can be hundreds of megabytes on some computers, so
    // we should use fallible new here.
    handleInfoBuf = MakeUniqueFallible<char[]>(handleInfoBufLen);
    if (!handleInfoBuf) {
      return Nothing();
    }

    ntStatus = ::NtQuerySystemInformation(
                 (SYSTEM_INFORMATION_CLASS) SystemExtendedHandleInformation,
                 handleInfoBuf.get(), handleInfoBufLen, &handleInfoBufLen);
    if (ntStatus == STATUS_INFO_LENGTH_MISMATCH) {
      continue;
    }

    if (!NT_SUCCESS(ntStatus)) {
      return Nothing();
    }

    break;
  }

  const DWORD ourPid = ::GetCurrentProcessId();
  Maybe<PVOID> kernelObject;
  static Maybe<USHORT> sectionObjTypeIndex;
  nsTHashtable<nsUint32HashKey> nonSectionObjTypes;
  nsDataHashtable<nsVoidPtrHashKey, DWORD> objMap;

  auto handleInfo = reinterpret_cast<SYSTEM_HANDLE_INFORMATION_EX*>(handleInfoBuf.get());

  for (ULONG index = 0; index < handleInfo->mHandleCount; ++index) {
    SYSTEM_HANDLE_TABLE_ENTRY_INFO_EX& curHandle = handleInfo->mHandles[index];

    HANDLE handle = reinterpret_cast<HANDLE>(curHandle.mHandle);

    // The mapping of the curHandle.mObjectTypeIndex field depends on the
    // underlying OS kernel. As we scan through the handle list, we record the
    // type indices such that we may use those values to skip over handles that
    // refer to non-section objects.
    if (sectionObjTypeIndex) {
      // If we know the type index for Sections, that's the fastest check...
      if (sectionObjTypeIndex.value() != curHandle.mObjectTypeIndex) {
        // Not a section
        continue;
      }
    } else if (nonSectionObjTypes.Contains(static_cast<uint32_t>(
                                             curHandle.mObjectTypeIndex))) {
      // Otherwise we check whether or not the object type is definitely _not_
      // a Section...
      continue;
    } else if (ourPid == curHandle.mPid) {
      // Otherwise we need to issue some system calls to find out the object
      // type corresponding to the current handle's type index.
      ULONG objTypeBufLen;
      ntStatus = ::NtQueryObject(handle, ObjectTypeInformation,
                                 nullptr, 0, &objTypeBufLen);
      if (ntStatus != STATUS_INFO_LENGTH_MISMATCH) {
        continue;
      }

      auto objTypeBuf = MakeUnique<char[]>(objTypeBufLen);
      ntStatus = ::NtQueryObject(handle, ObjectTypeInformation, objTypeBuf.get(),
                                 objTypeBufLen, &objTypeBufLen);
      if (!NT_SUCCESS(ntStatus)) {
        continue;
      }

      auto objType =
        reinterpret_cast<PUBLIC_OBJECT_TYPE_INFORMATION*>(objTypeBuf.get());

      // Now we check whether the object's type name matches "Section"
      nsDependentSubstring objTypeName(objType->TypeName.Buffer,
                                       objType->TypeName.Length / sizeof(wchar_t));
      if (!objTypeName.Equals(NS_LITERAL_STRING("Section"))) {
        nonSectionObjTypes.PutEntry(static_cast<uint32_t>(curHandle.mObjectTypeIndex));
        continue;
      }

      sectionObjTypeIndex = Some(curHandle.mObjectTypeIndex);
    }

    // At this point we know that curHandle references a Section object.
    // Now we can do some actual tests on it.

    if (ourPid != curHandle.mPid) {
      if (kernelObject && kernelObject.value() == curHandle.mObject) {
        // The kernel objects match -- we have found the remote pid!
        sUiaRemotePid = Some(curHandle.mPid);
        break;
      }

      // An object that is not ours. Since we do not yet know which kernel
      // object we're interested in, we'll save the current object for later.
      objMap.Put(curHandle.mObject, curHandle.mPid);
    } else if (handle == section.get()) {
      // This is the file mapping that we opened above. We save this mObject
      // in order to compare to Section objects opened by other processes.
      kernelObject = Some(curHandle.mObject);
    }
  }

  if (!kernelObject) {
    return Nothing();
  }

  if (!sUiaRemotePid) {
    // We found kernelObject *after* we saw the remote process's copy. Now we
    // must look it up in objMap.
    DWORD pid;
    if (objMap.Get(kernelObject.value(), &pid)) {
      sUiaRemotePid = Some(pid);
    }
  }

  if (!sUiaRemotePid) {
    return Nothing();
  }

  a11y::SetInstantiator(sUiaRemotePid.value());

  // Block if necessary
  nsCOMPtr<nsIFile> instantiator;
  if (a11y::GetInstantiator(getter_AddRefs(instantiator)) &&
      ShouldBlockUIAClient(instantiator)) {
    return Some(false);
  }

  return Some(true);
}
void CinematicTrigger::HandleOff()
{
	if (!m_bOn) return;

	for ( uint32 iWho = 0 ; iWho < MAX_CT_MESSAGES; iWho++ )
	{
		if ( m_hstrWhoPlaysDialogue[iWho] )
		{
			HOBJECT hWho;
			if ( LT_OK == FindNamedObject(m_hstrWhoPlaysDialogue[iWho], hWho) )
			{
				if ( IsKindOf(hWho, "CAI") )
				{
					CAI* pAI = (CAI*)g_pLTServer->HandleToObject(hWho);
					pAI->UnlinkCinematicTrigger(m_hObject);
				}
			}
		}
	}

    m_bOn = LTFALSE;

	// If we have a current speaker, make sure he is done talking...

	if (m_hCurSpeaker)
	{
        CCharacter* pChar = (CCharacter*)g_pLTServer->HandleToObject(m_hCurSpeaker);
		if (pChar)
		{
			pChar->StopDialogue();
		}

		// Clear our speaker...

        g_pLTServer->BreakInterObjectLink(m_hObject, m_hCurSpeaker);
        m_hCurSpeaker = LTNULL;
	}

	// Clear out our last speaker

	if (m_hLastSpeaker)
	{
        CCharacter* pChar = (CCharacter*)g_pLTServer->HandleToObject(m_hLastSpeaker);
		if (pChar)
		{
			pChar->StopDialogue(TRUE);
		}
        g_pLTServer->BreakInterObjectLink(m_hObject, m_hLastSpeaker);
        m_hLastSpeaker = LTNULL;
	}


	// Send the clean up trigger message...

	if (m_hstrCleanUpTriggerTarget && m_hstrCleanUpTriggerMsg)
	{
        SendTriggerMsgToObjects(this, g_pLTServer->GetStringData( m_hstrCleanUpTriggerTarget ), g_pLTServer->GetStringData( m_hstrCleanUpTriggerMsg ));
	}

	// Turn off the camera...

	if (m_hCamera && !m_bLeaveCameraOn)
	{
		SendTriggerMsgToObject(this, m_hCamera, FALSE, "OFF");
	}

	// Turn off the keyframer...

	if (m_hKeyFramer)
	{
		SendTriggerMsgToObject(this, m_hKeyFramer, FALSE, "OFF");
	}

    SetNextUpdate(m_hObject, 0.0f);

	if (m_bOneTimeOnly)
	{
		// Can't get rid of object if we're leaving the camera on ;)...

		if (!m_hCamera || !m_bLeaveCameraOn)
		{
			g_pLTServer->RemoveObject(m_hObject);
		}
	}
}
LTBOOL CinematicTrigger::UpdateDialogue()
{
    if (!g_pLTServer) return LTFALSE;

	// If we haven't yet done so, let all the cinematic participants know
	// they're under CinematicTrigger control

	if ( !m_bNotified )
	{
		for ( uint32 iWho = 0 ; iWho < MAX_CT_MESSAGES; iWho++ )
		{
			if ( m_hstrWhoPlaysDialogue[iWho] )
			{
				HOBJECT hWho;
				if ( LT_OK == FindNamedObject(m_hstrWhoPlaysDialogue[iWho], hWho) )
				{
					if ( IsKindOf(hWho, "CAI") )
					{
						CAI* pAI = (CAI*)g_pLTServer->HandleToObject(hWho);
						pAI->LinkCinematicTrigger(m_hObject);
					}
				}
			}
		}

        m_bNotified = LTTRUE;
	}

	// Now update...

    LTFLOAT fTime = g_pLTServer->GetTime();

	// See if we are playing a dialogue...
	BOOL bDone = FALSE;

	if (m_hCurSpeaker)
	{
		// If sound is done, stop it and wait for new sound...
        CCharacter* pChar = (CCharacter*)g_pLTServer->HandleToObject(m_hCurSpeaker);
		if (pChar)
		{
			bDone = !pChar->IsPlayingDialogue();
		}
	}

	if (bDone)
	{
		// Send message for our last reply (since the dialog is now done)...

		if (m_byLastReply)
		{
			SendReplyMessage(m_byLastReply);
		}

		m_byLastReply = m_byDecision;
		m_byDecision  = 0;

		// Clear our speaker...

        g_pLTServer->BreakInterObjectLink(m_hObject, m_hCurSpeaker);
        m_hCurSpeaker = LTNULL;

		if(m_byLastReply)
		{
			return StartDialogue(m_byLastReply);
		}

		m_nCurMessage++;

		if (m_nCurMessage < MAX_CT_MESSAGES)
		{
			m_fNextDialogueStart = fTime + m_fDelay[m_nCurMessage];
		}
		else
		{
            return LTFALSE;
		}
	}



	if (!m_hCurSpeaker)
	{
		// See if we're done...

		if (m_nCurMessage >= MAX_CT_MESSAGES || !m_hstrDialogue[m_nCurMessage])
		{
            return LTFALSE;
		}

		// Start next sound...

		if (m_fNextDialogueStart >= 0.0f && m_fNextDialogueStart <= fTime)
		{
			return StartDialogue();
		}
	}

    return LTTRUE;
}
示例#18
0
LTBOOL AI_Helicopter::HandleCommand(char** pTokens, int nArgs)
{
	// Let base class have a whack at it...

	if (CAIVehicle::HandleCommand(pTokens, nArgs)) return LTTRUE;

	// State-changing message

	for ( int iState = 0 ; iState < s_cStateMaps ; iState++ )
	{
		if ( !_stricmp(pTokens[0], s_aStateMaps[iState].szState) )
		{
			// Change states

			SetState(s_aStateMaps[iState].eState);
			HandleCommandParameters(pTokens, nArgs);

			return LTTRUE;
		}
	}

	// Non-state-changing messages

	if ( !_stricmp(pTokens[0], "FX") )
	{
		if ( nArgs != 4 )
		{
			g_pLTServer->CPrint("FX command needs 4 arguments! - FX IMPACT SOCKET \"IMPACTFX NAME\"");
			return LTTRUE;
		}

		if ( !_stricmp(pTokens[1], "IMPACT") )
		{
			HCLASS hClass = g_pLTServer->GetClass("Explosion");
			if (!hClass) return LTTRUE;

			LTVector vPos;

			g_pLTServer->GetObjectPos(m_hObject, &vPos);

			HMODELSOCKET hSocket;
			if ( LT_OK == g_pModelLT->GetSocket(m_hObject, pTokens[2], hSocket) )
			{
				LTransform tf;
				if ( LT_OK == g_pModelLT->GetSocketTransform(m_hObject, hSocket, tf, LTTRUE) )
				{
					if ( LT_OK == g_pTransLT->GetPos(tf, vPos) )
					{
					}
				}
			}

			IMPACTFX* pImpactFX = LTNULL;
			if ( pImpactFX = g_pFXButeMgr->GetImpactFX(pTokens[3]) )
			{
				EXPLOSIONCREATESTRUCT cs;
				cs.nImpactFX	 = pImpactFX->nId;
				cs.rRot			 = m_rRot;
				cs.vPos			 = vPos;
				cs.fDamageRadius = 0.0f;

				HMESSAGEWRITE hMessage = g_pLTServer->StartInstantSpecialEffectMessage(&vPos);
				g_pLTServer->WriteToMessageByte(hMessage, SFX_EXPLOSION_ID);
				cs.Write(g_pLTServer, hMessage);
				g_pLTServer->EndMessage2(hMessage, MESSAGE_NAGGLEFAST);
			}
		}
	}
	else if ( !_stricmp(pTokens[0], "LIGHTFOLLOW") )
	{
		if ( m_iObjectSearchLight == -1 ) return LTTRUE;

		HOBJECT hObject;
		if ( LT_OK == FindNamedObject(pTokens[1], hObject) )
		{
			if ( !IsKindOf(hObject, "ControlledSearchLight") ) return LTTRUE;

			ControlledSearchLight* pSearchLight = ((ControlledSearchLight*)m_apObjects[m_iObjectSearchLight]);
			if (pSearchLight)
			{
				pSearchLight->SetTarget(hObject);
			}
		}

		return LTTRUE;
	}

	return LTFALSE;
}
示例#19
0
AINode* CAINodeMgr::FindNearestObjectNode(CAI* pAI, EnumAINodeType eNodeType, const LTVector& vPos, const char* szClass)
{
    LTFLOAT fMinDistanceSqr = (float)INT_MAX;
    AINode* pClosestNode = LTNULL;

	// Get AIs Path Knowledge.

	CAIPathKnowledgeMgr* pPathKnowledgeMgr = LTNULL;
	if( pAI && pAI->GetPathKnowledgeMgr() )
	{
		pPathKnowledgeMgr = pAI->GetPathKnowledgeMgr();
	}

	AINode* pNode;
	AINODE_MAP::iterator it;
	for(it = m_mapAINodes.lower_bound(eNodeType); it != m_mapAINodes.upper_bound(eNodeType); ++it)
	{
		pNode = it->second;

		// Skip nodes in unreachable volumes.

		if( pPathKnowledgeMgr && 
			( pPathKnowledgeMgr->GetPathKnowledge( pNode->GetNodeContainingVolume() ) == CAIPathMgr::kPath_NoPathFound ) )
		{
			continue;
		}

		// Skip nodes that are not in volumes.

		if( !pNode->GetNodeContainingVolume() )
		{
			continue;
		}

		// Skip node if required alignment does not match.

		if( ( pNode->GetRequiredRelationTemplateID() != -1 ) &&
			( pNode->GetRequiredRelationTemplateID() != pAI->GetRelationMgr()->GetTemplateID() ) )
		{
			continue;
		}

		if( !pNode->NodeTypeIsActive( eNodeType ) )
		{
			continue;
		}

		if ( !pNode->IsLockedDisabledOrTimedOut() && pNode->HasObject() )
		{
            LTFLOAT fDistanceSqr = VEC_DISTSQR(vPos, pNode->GetPos());

			if ( (fDistanceSqr < fMinDistanceSqr) && (fDistanceSqr < pNode->GetRadiusSqr()) )
			{
				HOBJECT hObject;
				if ( LT_OK == FindNamedObject(pNode->GetObject(), hObject) )
				{
                    HCLASS hClass = g_pLTServer->GetClass((char*)szClass);

                    if ( g_pLTServer->IsKindOf(g_pLTServer->GetObjectClass(hObject), hClass) )
					{
						fMinDistanceSqr = fDistanceSqr;
						pClosestNode = pNode;
					}
				}
			}
		}
	}

	// Ensure that AI can pathfind to the destination node.
	// Ideally, we would like to do this check for each node as we iterate,
	// but that could result in multiple runs of BuildVolumePath() which
	// is expensive.  So instead we just check the final returned node.
	// The calling code can call this function again later, and will not get
	// this node again.

	if( pAI && pClosestNode )
	{
		AIVolume* pVolumeDest = pClosestNode->GetNodeContainingVolume();
		if( !g_pAIPathMgr->HasPath( pAI, pVolumeDest ) )
		{
			return LTNULL;
		}
	}

	return pClosestNode;
}
示例#20
0
bool ObjectRemover::AllObjectsCreated()
{
	HOBJECT ahObjects[kMaxGroups][kMaxObjectsPerGroup][128];
    memset(ahObjects, 0, sizeof(HOBJECT)*kMaxGroups*kMaxObjectsPerGroup*128);

	int cGroupsWithObjects = 0;

	{for ( int iGroup = 0 ; iGroup < kMaxGroups ; iGroup++ )
	{
        bool bGroupHasObjects = false;

		{for ( int iObject = 0 ; iObject < kMaxObjectsPerGroup ; iObject++ )
		{
			if ( !m_astrObjects[iGroup][iObject].empty() ) 
			{
				char szString[1024];
				strcpy(szString, m_astrObjects[iGroup][iObject].c_str());

				uint32 cTokens = 0;

				const char* szToken = strtok(szString, ";");

				while ( szToken )
				{
					HOBJECT hObject;
					if ( LT_OK == FindNamedObject(szToken, hObject) )
					{
						ahObjects[cGroupsWithObjects][iObject][cTokens++] = hObject;
						bGroupHasObjects = true;
					}

					szToken = strtok(NULL, ";");
				}
			}
		}}

		if ( bGroupHasObjects )
		{
			cGroupsWithObjects++;
		}
	}}

	// Remove the objects

    bool abRemoved[kMaxGroups];
    memset(abRemoved, false, sizeof(bool)*kMaxGroups);
	int iSafety = 50000;
	int cRemove = cGroupsWithObjects-m_cGroupsToKeep;

	while ( (cRemove > 0) && (--iSafety > 0) )
	{
		int iRemove = GetRandom(0, cGroupsWithObjects-1);
		if ( !abRemoved[iRemove] )
		{
			for ( int iObject = 0 ; iObject < kMaxObjectsPerGroup ; iObject++ )
			{
				for ( int iToken = 0 ; iToken < 128 ; iToken++ )
				{
					if ( ahObjects[iRemove][iObject][iToken] )
					{
						if ( IsAI(ahObjects[iRemove][iObject][iToken]) )
						{
							ILTBaseClass *pAI = g_pLTServer->HandleToObject( ahObjects[iRemove][iObject][iToken] );
							g_pCmdMgr->QueueMessage( this, pAI, "REMOVE" );
						}
						else
						{
							g_pLTServer->RemoveObject(ahObjects[iRemove][iObject][iToken]);
						}
					}
				}
			}

            abRemoved[iRemove] = true;
			cRemove--;
		}
	}

	// Remove ourselves...

    g_pLTServer->RemoveObject(m_hObject);

    return true;
}