Example #1
0
//Flags as defined by the cob standard
void CUnitScript::Explode(int piece, int flags)
{
	if (!PieceExists(piece)) {
		ShowUnitScriptError("Invalid piecenumber for explode");
		return;
	}

#ifndef _CONSOLE
	const float3 relPos = GetPiecePos(piece);
	const float3 absPos = unit->GetObjectSpacePos(relPos);

#ifdef TRACE_SYNC
	tracefile << "Cob explosion: ";
	tracefile << absPos.x << " " << absPos.y << " " << absPos.z << " " << piece << " " << flags << "\n";
#endif

	if (!(flags & PF_NoHeatCloud)) {
		// Do an explosion at the location first
		new CHeatCloudProjectile(nullptr, absPos, ZeroVector, 30, 30);
	}

	// If this is true, no stuff should fly off
	if (flags & PF_NONE)
		return;

	if (pieces[piece]->original == nullptr)
		return;

	if (flags & PF_Shatter) {
		Shatter(piece, absPos, unit->speed);
		return;
	}

	// This means that we are going to do a full fledged piece explosion!
	float3 baseSpeed = unit->speed;
	float3 explSpeed((0.5f - gs->randFloat()) * 6.0f, 1.2f + gs->randFloat() * 5.0f, (0.5f - gs->randFloat()) * 6.0f);

	if (unit->pos.y - CGround::GetApproximateHeight(unit->pos.x, unit->pos.z) > 15)
		explSpeed.y = (0.5f - gs->randFloat()) * 6.0f;

	if (baseSpeed.SqLength() > 9.0f) {
		const float l  = baseSpeed.Length();
		const float l2 = 3.0f + math::sqrt(l - 3.0f);
		baseSpeed *= (l2 / l);
	}

	explSpeed += baseSpeed;

	const float partSat = projectileHandler->GetParticleSaturation();

	int newFlags = 0;
	newFlags |= (PF_Explode    * ((flags & PF_Explode   ) != 0));
	newFlags |= (PF_Smoke      * ((flags & PF_Smoke     ) != 0) && partSat < 0.95f);
	newFlags |= (PF_Fire       * ((flags & PF_Fire      ) != 0) && partSat < 0.95f);
	newFlags |= (PF_NoCEGTrail * ((flags & PF_NoCEGTrail) != 0));
	newFlags |= (PF_Recursive  * ((flags & PF_Recursive ) != 0));

	new CPieceProjectile(unit, pieces[piece], absPos, explSpeed, newFlags, 0.5f);
#endif
}
Example #2
0
//Flags as defined by the cob standard
void CUnitScript::Explode(int piece, int flags)
{
	if (!PieceExists(piece)) {
		ShowUnitScriptError("Invalid piecenumber for explode");
		return;
	}

#ifndef _CONSOLE
	const float3 relPos = GetPiecePos(piece);
	const float3 absPos = unit->GetObjectSpacePos(relPos);

#ifdef TRACE_SYNC
	tracefile << "Cob explosion: ";
	tracefile << absPos.x << " " << absPos.y << " " << absPos.z << " " << piece << " " << flags << "\n";
#endif

	if (!(flags & PF_NoHeatCloud)) {
		// Do an explosion at the location first
		new CHeatCloudProjectile(NULL, absPos, ZeroVector, 30, 30);
	}

	// If this is true, no stuff should fly off
	if (flags & PF_NONE)
		return;

	// This means that we are going to do a full fledged piece explosion!
	float3 baseSpeed = unit->speed;
	float3 explSpeed((0.5f - gs->randFloat()) * 6.0f, 1.2f + gs->randFloat() * 5.0f, (0.5f - gs->randFloat()) * 6.0f);

	if (baseSpeed.SqLength() > 9) {
		const float l  = baseSpeed.Length();
		const float l2 = 3 + math::sqrt(l - 3);
		baseSpeed *= (l2 / l);
	}
	if (unit->pos.y - CGround::GetApproximateHeight(unit->pos.x, unit->pos.z) > 15) {
		explSpeed.y = (0.5f - gs->randFloat()) * 6.0f;
	}

	explSpeed += baseSpeed;

	// limit projectile speed to 12 elmos/frame (why?)
	if (false && explSpeed.SqLength() > (12.0f*12.0f)) {
		explSpeed = (explSpeed.Normalize() * 12.0f);
	}

	if (flags & PF_Shatter) {
		Shatter(piece, absPos, explSpeed);
		return;
	}

	if (pieces[piece]->original == NULL)
		return;

	// projectiles that don't fall could live forever
	int newflags = PF_Fall;

	const float partSat = projectileHandler->GetParticleSaturation();

	if (flags & PF_Explode) { newflags |= PF_Explode; }
	// if (flags & PF_Fall) { newflags |=  PF_Fall; }
	if ((flags & PF_Smoke) && partSat < 1.0f) { newflags |= PF_Smoke; }
	if ((flags & PF_Fire) && partSat < 0.95f) { newflags |= PF_Fire; }
	if (flags & PF_NoCEGTrail) { newflags |= PF_NoCEGTrail; }
	if (flags & PF_Recursive) { newflags |= PF_Recursive; }

	new CPieceProjectile(unit, pieces[piece], absPos, explSpeed, newflags, 0.5f);
#endif
}