⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 projectile.cpp

📁 Blood 2全套源码
💻 CPP
📖 第 1 页 / 共 2 页
字号:
	if (m_hHitObject)
	{
		g_pServerDE->BreakInterObjectLink(m_hObject, m_hHitObject);
		m_hHitObject = DFALSE;
	}
}

// ----------------------------------------------------------------------- //
//
//	ROUTINE:	CProjectile::DamageObjectsWithinRadius()
//
//	PURPOSE:	Damage the objects within our radius
//
// ----------------------------------------------------------------------- //

void CProjectile::DamageObjectsWithinRadius()
{
	CServerDE* pServerDE = BaseClass::GetServerDE();
	if (!pServerDE) return;

	DVector vPos;
	pServerDE->GetObjectPos(m_hObject, &vPos);

	DFLOAT fRadius = (DFLOAT)m_nRadius;

	DamageObjectsInRadius(m_hFiredFrom, this, vPos, fRadius, m_fDamage, m_nDamageType);
}


// ----------------------------------------------------------------------- //
//
//	ROUTINE:	CProjectile::AddImpact()
//
//	PURPOSE:	Add impact objects
//
// ----------------------------------------------------------------------- //

void CProjectile::AddImpact(DVector vPoint, DVector vNormal, HOBJECT hObj)
{
	// Compute a normal vector
	// Cast a ray to see what we hit
	DVector		tempPos;

	IntersectQuery iq;
	IntersectInfo  ii;
	SurfaceType eType = SURFTYPE_UNKNOWN;
	DBYTE nFX = 0;

	VEC_NORM(m_vDir);
	VEC_MULSCALAR(m_vDir, m_vDir, 2.0f);
	VEC_SUB(iq.m_From, vPoint, m_vDir);
	VEC_MULSCALAR(m_vDir, m_vDir, 10.0f);
	VEC_ADD(iq.m_To, vPoint, m_vDir);
	iq.m_Flags = INTERSECT_OBJECTS | IGNORE_NONSOLID;
	iq.m_FilterFn = NULL;
	iq.m_pUserData = NULL;	

	if (hObj && g_pServerDE->IntersectSegment(&iq, &ii))
	{
		VEC_COPY(vNormal, ii.m_Plane.m_Normal);
		eType = GetSurfaceType(ii.m_hObject, ii.m_hPoly);

		VEC_COPY(tempPos, ii.m_Point);
	}
	else	// Fake it
	{
		VEC_NEGATE(vNormal, m_vDir);

		VEC_COPY(tempPos, vPoint);
	}

	if(m_bExplosion) 
	{
		AddExplosion(tempPos, vNormal);
		nFX |= WFX_SCREENSHAKE;
	}

	if(m_bClientFX)
	{
		CServerDE* pServerDE = BaseClass::GetServerDE();
		if (!pServerDE) return;

/*		ObjectCreateStruct theStruct;
		INIT_OBJECTCREATESTRUCT(theStruct);

		VEC_COPY(theStruct.m_Pos, vPoint);

		HCLASS hClass = pServerDE->GetClass("CClientWeaponSFX");

		CClientWeaponSFX *pWeaponFX = DNULL;

		if(hClass)
			pWeaponFX = (CClientWeaponSFX*)pServerDE->CreateObject(hClass, &theStruct);
*/
		DDWORD	nFX = WFX_SCREENSHAKE;
		DDWORD	nExtras = WFX_EXTRA_DAMAGE;
		WeaponFXExtras	ext;
		ext.fDamage = m_fDamage;

//		if(pWeaponFX)
		SendWeaponSFXMessage(&vPoint, &vPoint, &vNormal, &vNormal, nFX, nExtras, &ext);
	}
}


// ----------------------------------------------------------------------- //
//
//	ROUTINE:	CProjectile::AddBloodImpact()
//
//	PURPOSE:	Add blood impacts objects
//
// ----------------------------------------------------------------------- //

void CProjectile::AddBloodImpact(DVector *vPos, DVector *vNormal, DFLOAT fDamage)
{
	CServerDE* pServerDE = BaseClass::GetServerDE();
	if (!pServerDE) return;

/*	ObjectCreateStruct theStruct;
	INIT_OBJECTCREATESTRUCT(theStruct);

	VEC_COPY(theStruct.m_Pos, *vPos);

	HCLASS hClass = pServerDE->GetClass("CClientWeaponSFX");

	CClientWeaponSFX *pWeaponFX = DNULL;

	if(hClass)
		pWeaponFX = (CClientWeaponSFX*)pServerDE->CreateObject(hClass, &theStruct);
*/
	DDWORD	nFX = WFX_BLOODSPURT | WFX_SPARKS;
	DDWORD	nExtras = WFX_EXTRA_DAMAGE | WFX_EXTRA_SURFACETYPE;
	WeaponFXExtras	ext;
	ext.fDamage = fDamage;
	ext.nSurface = (DBYTE)SURFTYPE_FLESH;

//	if(pWeaponFX)
	SendWeaponSFXMessage(vPos, vPos, vNormal, vNormal, nFX, nExtras, &ext);
}


// ----------------------------------------------------------------------- //
//
//	ROUTINE:	CProjectile::AddExplosion()
//
//	PURPOSE:	Add an explosion
//
// ----------------------------------------------------------------------- //

void CProjectile::AddExplosion(DVector vPos, DVector vNormal)
{
	CServerDE* pServerDE = BaseClass::GetServerDE();
	if (!pServerDE) return;

	DDWORD		nType = EXP_GRENADE;
	DVector		vUp;
	VEC_SET(vUp, 0.0f, 1.0f, 0.0f);

	HMESSAGEWRITE hMessage = pServerDE->StartInstantSpecialEffectMessage(&vPos);
	pServerDE->WriteToMessageByte(hMessage, SFX_EXPLOSIONFX_ID);

	pServerDE->WriteToMessageVector(hMessage, &vPos);
	pServerDE->WriteToMessageVector(hMessage, &vUp);
	pServerDE->WriteToMessageDWord(hMessage, nType);

	pServerDE->EndMessage2(hMessage, MESSAGE_GUARANTEED | MESSAGE_NAGGLEFAST);

	PlaySoundFromPos(&vPos, "Sounds\\Weapons\\c4\\explosion_1.wav", 1000.0f, SOUNDPRIORITY_MISC_MEDIUM);
}


// ----------------------------------------------------------------------- //
//
//	ROUTINE:	CProjectile::AddSmokeTrail()
//
//	PURPOSE:	Add a client-side smoke trail
//
// ----------------------------------------------------------------------- //

void CProjectile::AddSmokeTrail(DVector vVel)
{
	CServerDE* pServerDE = BaseClass::GetServerDE();
	if (!pServerDE) return;

	ObjectCreateStruct theStruct;
	INIT_OBJECTCREATESTRUCT(theStruct);

	DVector vPos;
	pServerDE->GetObjectPos(m_hObject, &vPos);
	VEC_COPY(theStruct.m_Pos, vPos);

	HCLASS hClass = pServerDE->GetClass("CClientSmokeTrail");

	CClientSmokeTrail* pTrail = DNULL;

	if (hClass)
	{
		pTrail = (CClientSmokeTrail*)pServerDE->CreateObject(hClass, &theStruct);
	}

	if (pTrail)
	{
		pTrail->Setup(vVel, DTRUE);
		m_hSmokeTrail = pTrail->m_hObject;
	}
}


// ----------------------------------------------------------------------- //
//
//	ROUTINE:	CProjectile::AddLight()
//
//	PURPOSE:	Add a dynamic light
//
// ----------------------------------------------------------------------- //

void CProjectile::AddLight(DFLOAT fRadius, DFLOAT fRed, DFLOAT fGreen, DFLOAT fBlue)
{
	CServerDE* pServerDE = BaseClass::GetServerDE();
	if (!pServerDE) return;

	m_vLightColor.x = fRed;
	m_vLightColor.y = fGreen;
	m_vLightColor.z = fBlue;

	if (fRadius)
	{
		ObjectCreateStruct ocStruct;
		INIT_OBJECTCREATESTRUCT(ocStruct);

		ocStruct.m_Flags = FLAG_VISIBLE;
		ocStruct.m_ObjectType = OT_LIGHT; 

		HCLASS hClass = pServerDE->GetClass("BaseClass");
		LPBASECLASS	pFlash = pServerDE->CreateObject(hClass, &ocStruct);

		if (pFlash)
		{
			m_hLight = pFlash->m_hObject;
			pServerDE->SetLightRadius(m_hLight, fRadius);
			pServerDE->SetLightColor(m_hLight, m_vLightColor.x, m_vLightColor.y, m_vLightColor.z);
		}
	}
}



// ----------------------------------------------------------------------- //
//
//	ROUTINE:	CProjectile::AddSparks
//
//	PURPOSE:	Add impact sparks
//
// ----------------------------------------------------------------------- //

void CProjectile::AddSparks(DVector vPos, DVector vNormal, DFLOAT fDamage, HOBJECT hObject)
{
	CServerDE* pServerDE = BaseClass::GetServerDE();
	if (!pServerDE) return;

	ObjectCreateStruct ocStruct;
	INIT_OBJECTCREATESTRUCT(ocStruct);

	VEC_COPY(ocStruct.m_Pos, vPos);

	HCLASS hClass = pServerDE->GetClass("CClientSparksSFX");

	CClientSparksSFX *pSpark = DNULL;

	if (hClass)
	{
		pSpark = (CClientSparksSFX *)pServerDE->CreateObject(hClass, &ocStruct);
	}

	if (pSpark)
	{
		DVector vColor1, vColor2;
		char* pFile;
		DBYTE nSparks = (DBYTE)fDamage;

		SurfaceType eType = GetSurfaceType(hObject, DNULL);

		switch(eType)
		{
			case SURFTYPE_FLESH:
			{
				VEC_SET(vColor1, 200.0f, 0.0f, 0.0f);
				VEC_SET(vColor2, 255.0f, 0.0f, 0.0f);

				pFile = "spritetextures\\particle1.dtx";

				pSpark->Setup(&vNormal, &vColor1, &vColor2, pFile, nSparks, 0.6f, 2.0f, 500.0f);
				break;
			}
			default:
			{
				VEC_SET(vColor1, 200.0f, 200.0, 200.0f);
				VEC_SET(vColor2, 200.0f, 200.0f, 0.0f);

				pFile = "spritetextures\\particle1.dtx";

				pSpark->Setup(&vNormal, &vColor1, &vColor2, pFile, nSparks, 0.4f, 2.0f, 500.0f);
				break;
			}
		}
	}

	return;
}


/*
// ----------------------------------------------------------------------- //
//
//	ROUTINE:	CProjectile::GetSurfaceType
//
//	PURPOSE:	Determines the surface type of a hit object
//
// ----------------------------------------------------------------------- //

SurfaceType CProjectile::GetSurfaceType(HOBJECT hObject)
{
	CServerDE* pServerDE = BaseClass::GetServerDE();
	if (!pServerDE || !hObject) return ST_UNKNOWN;
	
	SurfaceType eType = ST_UNKNOWN;

	if (pServerDE->GetWorldObject() == hObject)
	{
		eType = ST_WORLD;
	}
	else
	{
		HCLASS hObjClass  = pServerDE->GetObjectClass(hObject);
		HCLASS hCharacter = pServerDE->GetClass("CBaseCharacter");

		if (pServerDE->IsKindOf(hObjClass, hCharacter))
		{
			eType = ST_CHARACTER;
		}
	}

	return eType;
}

*/

void CProjectile::SetFlags(DDWORD dwFlags)
{
	CServerDE* pServerDE = BaseClass::GetServerDE();
	if (!pServerDE) return;

	m_dwFlags = dwFlags;
	pServerDE->SetObjectFlags(m_hObject, m_dwFlags);
}


// ----------------------------------------------------------------------- //
//
//	ROUTINE:	CProjectile::Save
//
//	PURPOSE:	Save the object
//
// ----------------------------------------------------------------------- //

void CProjectile::Save(HMESSAGEWRITE hWrite, DDWORD dwSaveFlags)
{
	CServerDE* pServerDE = GetServerDE();
	if (!pServerDE || !hWrite) return;

	DFLOAT fTime = pServerDE->GetTime();

	pServerDE->WriteToMessageVector(hWrite, &m_vDir);
	pServerDE->WriteToMessageFloat(hWrite, m_fVelocity);
	pServerDE->WriteToMessageDWord(hWrite, m_dwFlags);

	pServerDE->WriteToMessageByte(hWrite, m_nDamageType);
//		HOBJECT			m_hFiredFrom;			// Who fired us?  Can't tell
	pServerDE->WriteToMessageDWord(hWrite, m_nRadius);
	pServerDE->WriteToMessageFloat(hWrite, m_fStartTime - fTime);
	pServerDE->WriteToMessageByte(hWrite, m_bRemoveFromWorld);
	pServerDE->WriteToMessageFloat(hWrite, m_fDamage);
	pServerDE->WriteToMessageFloat(hWrite, m_fLifeTime);
	pServerDE->WriteToMessageDWord(hWrite, m_nDamageMsgID);

//		DBOOL			m_bSmokeTrail;			// Do we generate a smoke trail

	pServerDE->WriteToMessageByte(hWrite, m_bShockwave);
	pServerDE->WriteToMessageByte(hWrite, m_bExplosion);
	pServerDE->WriteToMessageByte(hWrite, m_bSparks);
	pServerDE->WriteToMessageVector(hWrite, &m_vShockwaveScaleMin);
	pServerDE->WriteToMessageVector(hWrite, &m_vShockwaveScaleMax);
	pServerDE->WriteToMessageVector(hWrite, &m_vLightColor);
	pServerDE->WriteToMessageFloat(hWrite, m_fShockwaveDuration);
	pServerDE->WriteToMessageHString(hWrite,m_hstrShockwaveFilename);

	pServerDE->WriteToMessageVector(hWrite, &m_vDims);
	pServerDE->WriteToMessageByte(hWrite, m_bExplode);

	// Special members
	pServerDE->WriteToMessageVector(hWrite, &m_LastPos);
	pServerDE->WriteToMessageByte(hWrite, m_bArmed);
	pServerDE->WriteToMessageFloat(hWrite, m_fPitchVel);
	pServerDE->WriteToMessageFloat(hWrite, m_fYawVel);
	pServerDE->WriteToMessageFloat(hWrite, m_fPitch);
	pServerDE->WriteToMessageFloat(hWrite, m_fYaw);
}


// ----------------------------------------------------------------------- //
//
//	ROUTINE:	CProjectile::Load
//
//	PURPOSE:	Load the object
//
// ----------------------------------------------------------------------- //

void CProjectile::Load(HMESSAGEREAD hRead, DDWORD dwLoadFlags)
{
	CServerDE* pServerDE = GetServerDE();
	if (!pServerDE || !hRead) return;

	DFLOAT fTime = pServerDE->GetTime();

	pServerDE->ReadFromMessageVector(hRead, &m_vDir);
	m_fVelocity				= pServerDE->ReadFromMessageFloat(hRead);
	m_dwFlags				= pServerDE->ReadFromMessageDWord(hRead);

	m_nDamageType			= pServerDE->ReadFromMessageByte(hRead);
//		HOBJECT			m_hFiredFrom;			// Who fired us?  Can't tell
	m_nRadius				= pServerDE->ReadFromMessageDWord(hRead);
	m_fStartTime			= pServerDE->ReadFromMessageFloat(hRead) + fTime;
	m_bRemoveFromWorld		= pServerDE->ReadFromMessageByte(hRead);
	m_fDamage				= pServerDE->ReadFromMessageFloat(hRead);
	m_fLifeTime				= pServerDE->ReadFromMessageFloat(hRead);
	m_nDamageMsgID			= pServerDE->ReadFromMessageDWord(hRead);

//		DBOOL			m_bSmokeTrail;			// Do we generate a smoke trail

	m_bShockwave			= pServerDE->ReadFromMessageByte(hRead);
	m_bExplosion			= pServerDE->ReadFromMessageByte(hRead);
	m_bSparks				= pServerDE->ReadFromMessageByte(hRead);
	pServerDE->ReadFromMessageVector(hRead, &m_vShockwaveScaleMin);
	pServerDE->ReadFromMessageVector(hRead, &m_vShockwaveScaleMax);
	pServerDE->ReadFromMessageVector(hRead, &m_vLightColor);
	m_fShockwaveDuration	= pServerDE->ReadFromMessageFloat(hRead);
	m_hstrShockwaveFilename	= pServerDE->ReadFromMessageHString(hRead);

	pServerDE->ReadFromMessageVector(hRead, &m_vDims);
	m_bExplode				= pServerDE->ReadFromMessageByte(hRead);

	// Special members
	pServerDE->ReadFromMessageVector(hRead, &m_LastPos);
	m_bArmed	= pServerDE->ReadFromMessageByte(hRead);
	m_fPitchVel	= pServerDE->ReadFromMessageFloat(hRead);
	m_fYawVel	= pServerDE->ReadFromMessageFloat(hRead);
	m_fPitch	= pServerDE->ReadFromMessageFloat(hRead);
	m_fYaw		= pServerDE->ReadFromMessageFloat(hRead);
}



⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -