Пример #1
0
	void EditorPoint::setMinAndMaxShiftPoint(int p_index)
	{
		if (p_index >= 0 && p_index < m_track.getPointCount())
		{
			const TrackPoint& trackPoint = m_track.getPoint(p_index);

			float minShift = -1.0f - trackPoint.getShift();
			float maxShift = 1.0f - trackPoint.getShift();
			float radius = trackPoint.getRadius();

			CL_Vec2f guide = m_gfxLevel.getTrackTriangulator().getGuide(p_index);

			guide /= guide.length();

			CL_Vec2f minShiftGuide = guide;
			setToPerpendicular(minShiftGuide, true);
			minShiftGuide *= radius * minShift;

			CL_Vec2f maxShiftGuide = guide;
			setToPerpendicular(maxShiftGuide, true);
			maxShiftGuide *= radius * maxShift;

			const CL_Pointf& pos = trackPoint.getPosition();

			m_impl->m_minShiftPoint = pos + minShiftGuide;
			m_impl->m_maxShiftPoint = pos + maxShiftGuide;
		}
	}
Пример #2
0
void Car::applyCollision(const CL_LineSegment2f &p_seg)
{
	static const float DAMAGE_MULT = 0.2f;

	const float side = -p_seg.point_right_of_line(m_impl->m_position);

	const CL_Vec2f segVec = p_seg.q - p_seg.p;

	// need front normal (crash side)
	CL_Vec2f fnormal(segVec.y, -segVec.x); // right side normal
	fnormal.normalize();

	if (side < 0) {
		fnormal *= -1;
	}

	// move away
	m_impl->m_position += (fnormal * fabs(m_impl->m_speed));

	// calculate collision angle to estaminate speed reduction
	CL_Angle angleDiff(m_impl->m_phyMoveRot - m_impl->vecToAngle(fnormal));
	Workarounds::clAngleNormalize180(&angleDiff);

	const float colAngleDeg = fabs(angleDiff.to_degrees()) - 90.0f;
	const float reduction = fabs(1.0f - fabs(colAngleDeg - 90.0f) / 90.0f);

	// calculate and apply damage
	const float damage = m_impl->m_speed * reduction * DAMAGE_MULT;
	m_impl->m_damage =
			Math::Float::reduce(m_impl->m_damage + damage, 0.0f, 1.0f);

	cl_log_event(LOG_DEBUG, "damage: %1, total: %2", damage, m_impl->m_damage);

	// reduce speed
	m_impl->m_speed -= m_impl->m_speed * reduction;

	// bounce movement vector and angle away

	// get mirror point
	if (m_impl->m_phyMoveVec.length() > 0.01f) {
		m_impl->m_phyMoveVec.normalize();

		const float lengthProj = m_impl->m_phyMoveVec.length() * cos(segVec.angle(m_impl->m_phyMoveVec).to_radians());
		const CL_Vec2f mirrorPoint(segVec * (lengthProj / segVec.length()));

		// invert move vector by mirror point
		const CL_Vec2f mirrorVec = (m_impl->m_phyMoveVec - mirrorPoint) * -1;
		m_impl->m_phyMoveVec = mirrorPoint + mirrorVec;

		// update physics angle
		m_impl->m_phyMoveRot = m_impl->vecToAngle(m_impl->m_phyMoveVec);

	}

}
Пример #3
0
void Misil::mover(float dt)
{
	if(perseguidor)
	{
		int tiempdodesdedisparo= CL_System::get_time() - tiempodisparo;

		if(tiempdodesdedisparo >= 10)
		{	
			CL_Vec2f vector = Posicion - TargetTanque->getPos();
			
			float distancia = vector.length();
			mundo->AgregarCadenaChat(cl_format("%1",distancia));

			CL_Vec2f up(0.0f, 1.0f);
			float angulodest = up.angle(vector).to_degrees();

			/*if(TargetTanque->getPos().x < Posicion.x)
				angulodest = 360.0f - angulo;*/
			/*	else
				angulodest = 360.0f  angulo;*/

			angulodelta = angulodest - angulo;

			if(distancia < 150)
			{
				if(angulodelta > 0)
					angulodelta +=5;
			}
				
			if(angulodelta > 180.0f)	
			{
				angulodelta -= 360.0f;
				angulo += 360.0f;
			}
			if(angulodelta < -180.0f)
			{
				angulodelta += 360.0f;
				angulo -= 360.0f;
			}

			angulo +=angulodelta*dt/velocidad;

			setAngulo(angulo);
		}

	}

	Posicion.x += dt* float(sin(angulo* CL_PI / 180.0f));
	Posicion.y += dt* float(-cos(angulo * CL_PI / 180.0f));
	collisionMisil->set_translation(Posicion.x, Posicion.y);
}
Пример #4
0
	void EditorPoint::getShiftRect(int p_index, int* x1, int* y1, int* x2, int* y2)
	{
		const TrackPoint& p_trackPoint = m_track.getPoint(p_index);

		CL_Vec2f guide = m_gfxLevel.getTrackTriangulator().getGuide(p_index);

		float guideLength = guide.length();
		guide *= p_trackPoint.getShift() * p_trackPoint.getRadius();
		guide /= guideLength;

		setToPerpendicular(guide, false);

		const CL_Pointf& pos = p_trackPoint.getPosition();

		*x1 = pos.x;
		*y1 = pos.y;
		*x2 = pos.x + guide.x;
		*y2 = pos.y + guide.y;
	}
Пример #5
0
bool IntersectRaySphere(CL_Vec2f p, CL_Vec2f d, rtCircle s, float &t, CL_Vec2f &q)
{

	CL_Vec2f m = p - s.c;
	float b = m.dot(d);
	float c = m.dot(m) - s.r * s.r;

	// Exit if r’s origin outside s (c > 0) and r pointing away from s (b > 0)
	if (c > 0.0f && b > 0.0f) return false;
	float discr = b*b - c;
	// A negative discriminant corresponds to ray missing sphere
	if (discr < 0.0f) return false;
	// Ray now found to intersect sphere, compute smallest t value of intersection
	t = -b - sqrt(discr);
	// If t is negative, ray started inside sphere so clamp t to zero
	if (t < 0.0f) t = 0.0f;
	q=p+(d*t);

	return true;
}
Пример #6
0
CL_Angle CarImpl::vecToAngle(const CL_Vec2f &p_vec)
{
	const static CL_Vec2f ANGLE_ZERO(1.0f, 0.0f);
	CL_Angle angle = p_vec.angle(ANGLE_ZERO);

	if (p_vec.y < 0) {
		angle.set_radians(-angle.to_radians());
	}

	return angle;

}
Пример #7
0
bool CircleSegmentIntersect(CL_Vec2f C, float r, CL_Vec2f A, CL_Vec2f B, CL_Vec2f& P)
{
	CL_Vec2f AC = C - A;
	CL_Vec2f AB = B - A;
	float ab2 = AB.dot(AB);
	float acab = AC.dot(AB);
	float t = acab / ab2;

	if (t < 0.0f) 
		t = 0.0f;
	else if (t > 1.0f) 
		t = 1.0f;

	P = A + AB * t;

	CL_Vec2f H = P - C;
	float h2 = H.dot(H);
	float r2 = r * r;

	if(h2 > r2) 
		return false;
	else
		return true;
}
Пример #8
0
void  DrawLine( GLuint rgba,   float ax, float ay, float bx, float by, float lineWidth )
{
	SetupOrtho();
	//g_globalBatcher.Flush();

	glDisable( GL_TEXTURE_2D );

	glEnableClientState(GL_VERTEX_ARRAY);	
	glDisableClientState(GL_TEXTURE_COORD_ARRAY);
	glDisable(GL_CULL_FACE);

	static GLfloat	vertices[3*4];

	CL_Vec2f start = CL_Vec2f(ax, ay);
	CL_Vec2f end = CL_Vec2f(bx, by);

	float dx = ax - bx;
	float dy = ay - by;

	CL_Vec2f rightSide = CL_Vec2f(dy, -dx);

	if (rightSide.length() > 0) 
	{
		rightSide.normalize();
		rightSide *= lineWidth/2;
	}
	
	CL_Vec2f  leftSide =CL_Vec2f(-dy, dx);
	
	if (leftSide.length() > 0) 
	{
		leftSide.normalize();
		leftSide *= lineWidth/2;
	}

	CL_Vec2f one = leftSide + start;

	CL_Vec2f two = rightSide + start;

	CL_Vec2f three = rightSide + end;

	CL_Vec2f four = leftSide = end;

	vertices[0*3+0] = one.x; vertices[0*3+1] = one.y;
	vertices[1*3+0] = two.x; vertices[1*3+1] = two.y;
	vertices[2*3+0] = three.x; vertices[2*3+1] = three.y;
	vertices[3*3+0] = four.x; vertices[3*3+1] = four.y;

	//set the Z
	vertices[0*3+2] = 0;
	vertices[1*3+2] = 0;
	vertices[2*3+2] = 0;
	vertices[3*3+2] = 0;
	
	glVertexPointer(3, GL_FLOAT, 0, vertices);
	//glColor4f(1, 1, 1, 1);
	glEnable( GL_BLEND );
	glColor4x( (rgba >>8 & 0xFF)*256,  (rgba>>16& 0xFF)*256, (rgba>>24& 0xFF)*256, (rgba&0xFF)*256);

	glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
	glColor4x(1 << 16, 1 << 16, 1 << 16, 1 << 16);

	glEnable(GL_CULL_FACE);

	glDisable( GL_BLEND );
	glEnable( GL_TEXTURE_2D );
	glEnableClientState(GL_TEXTURE_COORD_ARRAY);	
	CHECK_GL_ERROR();
}
Пример #9
0
void CarImpl::update1_60() {
	
	static const float BRAKE_POWER = 0.1f;
	static const float ACCEL_POWER = 0.014f;
	static const float SPEED_LIMIT = 15.0f;
	static const float WHEEL_TURN_SPEED = 1.0f / 10.0f;
	static const float TURN_POWER  = (2 * CL_PI / 360.0f) * 2.5f;
	static const float MOV_ALIGN_POWER = TURN_POWER / 2.0f;
	static const float ROT_ALIGN_POWER = TURN_POWER * 0.7f;
	static const float AIR_RESITANCE = 0.003f; // per one speed unit
	static const float DRIFT_SPEED_REDUCTION_RATE = 0.1f;

	// speed limit under what physics angle reduction will be more aggressive
	static const float LOWER_SPEED_ANGLE_REDUCTION = 6.0f;
	// speed limit under what angle difference will be lower than normal
	static const float LOWER_SPEED_ROTATION_REDUCTION = 6.0f;
	// speed limit under what turn power will decrease
	static const float LOWER_SPEED_TURN_REDUCTION = 2.0f;


	// increase the iteration id
	// be aware of 32-bit integer limit
	if (m_iterId != std::numeric_limits<int32_t>::max()) {
		m_iterId++;
	} else {
		m_iterId = 0;
	}

	// don't do anything if car is locked
	if (m_inputLocked) {
		return;
	}
	
	const float prevSpeed = m_speed; // for m_phySpeedDelta

	// apply inputs to speed
	if (m_inputState.brake) {
		m_speed -= BRAKE_POWER;
	} else if (m_inputState.accel) {
		// only if not choking
		if (!isChoking()) {
			m_chocking = false;
			m_speed += (SPEED_LIMIT - m_speed) * ACCEL_POWER;
		} else {
			m_chocking = true;
		}
	}
	
	// rotate steering wheels
	const float diff = m_inputState.turn - m_phyWheelsTurn;

	if (fabs(diff) > WHEEL_TURN_SPEED) {
		m_phyWheelsTurn += diff > 0.0f ? WHEEL_TURN_SPEED : -WHEEL_TURN_SPEED;
	} else {
		m_phyWheelsTurn = m_inputState.turn;
	}

	const float absSpeed = fabs(m_speed);

	// calculate rotations
	if (m_phyWheelsTurn != 0.0f) {

		// rotate corpse and later physics movement
		CL_Angle turnAngle(TURN_POWER * m_phyWheelsTurn, cl_radians);

		if (absSpeed <= LOWER_SPEED_TURN_REDUCTION) {
			// reduce turn if car speed is too low
			turnAngle.set_radians(turnAngle.to_radians() * (absSpeed / LOWER_SPEED_TURN_REDUCTION));
		}

		if (m_speed > 0.0f) {
			m_rotation += turnAngle;
		} else {
			m_rotation -= turnAngle;
		}

		// rotate corpse and physics movement
		if (absSpeed > LOWER_SPEED_ROTATION_REDUCTION) {
			alignRotation(m_phyMoveRot, m_rotation, MOV_ALIGN_POWER);
		} else {
			alignRotation(m_phyMoveRot, m_rotation, MOV_ALIGN_POWER * ((LOWER_SPEED_ROTATION_REDUCTION + 1.0f) - absSpeed));
		}

	} else {

		// align corpse back to physics movement
		alignRotation(m_rotation, m_phyMoveRot, MOV_ALIGN_POWER);

		// makes car stop rotating if speed is too low
		if (absSpeed > LOWER_SPEED_ANGLE_REDUCTION) {
			alignRotation(m_phyMoveRot, m_rotation, ROT_ALIGN_POWER);
		} else {
			alignRotation(m_phyMoveRot, m_rotation, ROT_ALIGN_POWER * ((LOWER_SPEED_ANGLE_REDUCTION + 1.0f) - absSpeed));
		}

		// normalize rotations only when equal
		if (m_rotation == m_phyMoveRot) {
			Workarounds::clAngleNormalize(&m_rotation);
			Workarounds::clAngleNormalize(&m_phyMoveRot);
		}

	}

	Workarounds::clAngleNormalize(&m_phyMoveRot);
	Workarounds::clAngleNormalize(&m_rotation);


	// reduce speed
	const CL_Angle diffAngle = m_rotation - m_phyMoveRot;
	float diffDegAbs = fabs(diffAngle.to_degrees());

	if (diffDegAbs > 0.1f) {

		CL_Angle diffAngleNorm = diffAngle;
		Workarounds::clAngleNormalize180(&diffAngleNorm);

		// 0.0 when going straight, 1.0 when 90 deg, > 1.0 when more than 90 deg
		const float angleRate = fabs(1.0f - (fabs(diffAngleNorm.to_degrees()) - 90.0f) / 90.0f);
		const float speedReduction = -DRIFT_SPEED_REDUCTION_RATE * angleRate;

		if (absSpeed > speedReduction) {
			m_speed += m_speed > 0.0f ? speedReduction : -speedReduction;
		} else {
			m_speed = 0.0f;
		}
	}

	// car cannot travel too quickly
	m_speed -= m_speed * AIR_RESITANCE;

	// calculate next move vector
	const float m_rotationRad = m_phyMoveRot.to_radians();

	m_phyMoveVec.x = cos(m_rotationRad);
	m_phyMoveVec.y = sin(m_rotationRad);

	m_phyMoveVec.normalize();
	m_phyMoveVec *= m_speed;

	// apply movement (invert y)
	m_position.x += m_phyMoveVec.x;
	m_position.y += m_phyMoveVec.y;

	// set speed delta
	m_phySpeedDelta = m_speed - prevSpeed;


#if defined(CLIENT)
#if !defined(NDEBUG)
	// print debug information
	DebugLayer *dbgl = Gfx::Stage::getDebugLayer();

	dbgl->putMessage("speed", cl_format("%1", m_speed));
//	if (!m_level) {
//		const float resistance = m_level->getResistance(m_position.x, m_position.y);
//		dbgl->putMessage("resist", cl_format("%1", resistance));
//	}
#endif // NDEBUG
#endif // CLIENT
}