Пример #1
0
bool KX_ConstraintActuator::RayHit(KX_ClientObjectInfo *client, KX_RayCast *result, void *UNUSED(data))
{

	m_hitObject = client->m_gameobject;
	
	bool bFound = false;

	if (m_property.empty())
	{
		bFound = true;
	}
	else
	{
		if (m_option & KX_ACT_CONSTRAINT_MATERIAL) {
			for (unsigned int i = 0; i < m_hitObject->GetMeshCount(); ++i) {
				RAS_MeshObject *meshObj = m_hitObject->GetMesh(i);
				for (unsigned int j = 0; j < meshObj->NumMaterials(); ++j) {
					bFound = (m_property == std::string(meshObj->GetMaterialName(j), 2));
					if (bFound)
						break;
				}
			}
		}
		else {
			bFound = m_hitObject->GetProperty(m_property) != NULL;
		}
	}
	// update the hit status
	result->m_hitFound = bFound;
	// stop looking
	return true;
}
/* this function is used to pre-filter the object before casting the ray on them.
 * This is useful for "X-Ray" option when we want to see "through" unwanted object.
 */
bool KX_MouseFocusSensor::NeedRayCast(KX_ClientObjectInfo* client)
{
	KX_GameObject *hitKXObj = client->m_gameobject;

	if (client->m_type > KX_ClientObjectInfo::ACTOR)
	{
		// Unknown type of object, skip it.
		// Should not occur as the sensor objects are filtered in RayTest()
		printf("Invalid client type %d found ray casting\n", client->m_type);
		return false;
	}
	if (m_bXRay && m_propertyname.Length() != 0)
	{
		if (m_bFindMaterial)
		{
			bool found = false;
			for (unsigned int i = 0; i < hitKXObj->GetMeshCount(); ++i) {
				RAS_MeshObject *meshObj = hitKXObj->GetMesh(i);
				for (unsigned int j = 0; j < meshObj->NumMaterials(); ++j) {
					found = strcmp(m_propertyname.ReadPtr(), meshObj->GetMaterialName(j).ReadPtr() + 2) == 0;
					if (found)
						break;
				}
			}
			if (!found)
				return false;
		}
		else
		{
			if (hitKXObj->GetProperty(m_propertyname) == NULL)
				return false;
		}
	}
	return true;
}
Пример #3
0
bool	KX_TouchSensor::NewHandleCollision(void*object1,void*object2,const PHY_CollData* colldata)
{
//	KX_TouchEventManager* toucheventmgr = (KX_TouchEventManager*)m_eventmgr;
	KX_GameObject* parent = (KX_GameObject*)GetParent();

	// need the mapping from PHY_IPhysicsController to gameobjects now

	KX_ClientObjectInfo *client_info = static_cast<KX_ClientObjectInfo*> (object1 == m_physCtrl?
					((PHY_IPhysicsController*)object2)->GetNewClientInfo():
					((PHY_IPhysicsController*)object1)->GetNewClientInfo());

	KX_GameObject* gameobj = ( client_info ?
			client_info->m_gameobject :
			NULL);

	// add the same check as in SCA_ISensor::Activate(),
	// we don't want to record collision when the sensor is not active.
	if (m_links && !m_suspended &&
		gameobj && (gameobj != parent) && client_info->isActor())
	{

		bool found = m_touchedpropname.IsEmpty();
		bool hitMaterial = false;
		if (!found)
		{
			if (m_bFindMaterial) {
				for (unsigned int i = 0; i < gameobj->GetMeshCount(); ++i) {
					RAS_MeshObject *meshObj = gameobj->GetMesh(i);
					for (unsigned int j = 0; j < meshObj->NumMaterials(); ++j) {
						found = strcmp(m_touchedpropname.ReadPtr(), meshObj->GetMaterialName(j).ReadPtr() + 2) == 0;
						if (found) {
							hitMaterial = true;
							break;
						}
					}
				}
			}
			else {
				found = (gameobj->GetProperty(m_touchedpropname) != NULL);
			}
		}
		if (found)
		{
			if (!m_colliders->SearchValue(gameobj)) {
				m_colliders->Add(gameobj->AddRef());

				if (m_bTouchPulse)
					m_bColliderHash += (uint_ptr)(static_cast<void *>(&gameobj));
			}
			m_bTriggered = true;
			m_hitObject = gameobj;
			m_hitMaterial = hitMaterial;
			//printf("KX_TouchSensor::HandleCollision\n");
		}

	}
	return false; // was DT_CONTINUE but this was defined in sumo as false.
}
bool KX_MouseFocusSensor::RayHit(KX_ClientObjectInfo *client_info, KX_RayCast *result, void * const data)
{
	KX_GameObject* hitKXObj = client_info->m_gameobject;
	
	/* Is this me? In the ray test, there are a lot of extra checks
	 * for aliasing artifacts from self-hits. That doesn't happen
	 * here, so a simple test suffices. Or does the camera also get
	 * self-hits? (No, and the raysensor shouldn't do it either, since
	 * self-hits are excluded by setting the correct ignore-object.)
	 * Hitspots now become valid. */
	KX_GameObject* thisObj = (KX_GameObject*) GetParent();

	bool bFound = false;

	if ((m_focusmode == 2) || hitKXObj == thisObj)
	{
		if (m_propertyname.Length() == 0)
		{
			bFound = true;
		}
		else
		{
			if (m_bFindMaterial) {
				for (unsigned int i = 0; i < hitKXObj->GetMeshCount(); ++i) {
					RAS_MeshObject *meshObj = hitKXObj->GetMesh(i);
					for (unsigned int j = 0; j < meshObj->NumMaterials(); ++j) {
						bFound = strcmp(m_propertyname.ReadPtr(), meshObj->GetMaterialName(j).ReadPtr() + 2) == 0;
						if (bFound)
							break;
					}
				}
			}
			else {
				bFound = hitKXObj->GetProperty(m_propertyname) != NULL;
			}
		}

		if (bFound)
		{
			m_hitObject = hitKXObj;
			m_hitPosition = result->m_hitPoint;
			m_hitNormal = result->m_hitNormal;
			m_hitUV = result->m_hitUV;
			return true;
		}		
	}
	
	return true;     // object must be visible to trigger
	//return false;  // occluded objects can trigger
}
Пример #5
0
// this function is called only for sensor objects
// return true if the controller can collide with the object
bool KX_CollisionSensor::BroadPhaseSensorFilterCollision(void *obj1, void *obj2)
{
	BLI_assert(obj1 == m_physCtrl && obj2);

	KX_GameObject *myobj = (KX_GameObject *)GetParent();
	KX_GameObject *myparent = myobj->GetParent();
	KX_ClientObjectInfo *client_info = static_cast<KX_ClientObjectInfo *>(((PHY_IPhysicsController *)obj2)->GetNewClientInfo());
	KX_ClientObjectInfo *my_client_info = static_cast<KX_ClientObjectInfo *>(m_physCtrl->GetNewClientInfo());
	KX_GameObject *otherobj = (client_info ? client_info->m_gameobject : NULL);

	// we can only check on persistent characteristic: m_link and m_suspended are not
	// good candidate because they are transient. That must be handled at another level
	if (!otherobj ||
	    otherobj == myparent ||     // don't interact with our parent
	    (my_client_info->m_type == KX_ClientObjectInfo::OBACTORSENSOR &&
	     client_info->m_type != KX_ClientObjectInfo::ACTOR))    // only with actor objects
	{
		return false;
	}

	bool found = m_touchedpropname.empty();
	if (!found) {
		if (m_bFindMaterial) {
			for (unsigned int i = 0; i < otherobj->GetMeshCount(); ++i) {
				RAS_MeshObject *meshObj = otherobj->GetMesh(i);
				for (unsigned int j = 0; j < meshObj->NumMaterials(); ++j) {
					found = (m_touchedpropname == std::string(meshObj->GetMaterialName(j), 2));
					if (found) {
						break;
					}
				}
			}
		}
		else {
			found = (otherobj->GetProperty(m_touchedpropname) != NULL);
		}
	}
	return found;
}