Example #1
0
void R3DCamera::Rotate(float angle, float x, float y, float z)
{
    // Get direction vector
    T_GLVector3f vecDir, vecNew;
    Vec3fSub(&vecDir, this->vLookAt, this->vEye);

    // Compute sin and cos of the angle
    float sinAng = (float)sin(angle);
    float cosAng = (float)cos(angle);

    // Compute new x position
    vecNew.x = (cosAng + (1 - cosAng) * x * x) * vecDir.x;
    vecNew.x += ((1 - cosAng) * x * y - z * sinAng) * vecDir.y;
    vecNew.x += ((1 - cosAng) * x * z + y * sinAng) * vecDir.z;
    // Compute new y position
    vecNew.y = ((1 - cosAng) * x * y + z * sinAng) * vecDir.x;
    vecNew.y += (cosAng + (1 - cosAng) * y * y) * vecDir.y;
    vecNew.z += ((1 - cosAng) * y * z - x * sinAng) * vecDir.z;
    // Compute new z position
    vecNew.z = ((1 - cosAng) * x * z - y * sinAng) * vecDir.x;
    vecNew.z += ((1 - cosAng) * y * z + x * sinAng) * vecDir.y;
    vecNew.z += (cosAng + (1 - cosAng) * z * z) * vecDir.z;

    // Compute new rotated look at vector
    Vec3fAdd(&this->vLookAt, this->vEye, vecNew);
}
void CTrackingMissile::Update(void)
{
	CQuaternion q;
	float t;

	m_Age = g_time - m_CreationTime;

   if(m_Age > m_LifeTime)
   {
      Die();
      return;
   }

	if (!m_Tracking)
	{
		if (m_Age <= 0.4f)
		{
			if (m_FlyLeft)
				m_RenderObj.MoveRight(-20.0f * g_FrameTime, 0);
			else
				m_RenderObj.MoveRight(20.0f * g_FrameTime, 0);
	
			t = m_Age;
			QuatSlerp(&q, &m_Q0, &m_Q1, t * 2.5f);
			m_RenderObj.GetFrame(0)->SetOrientation(&q);
		}
		else if (m_Age <= 0.8f && !m_Target)
		{
			t = m_Age - 0.4f;
			QuatSlerp(&q, &m_Q1, &m_Q2, t * 2.5f);
			m_RenderObj.GetFrame(0)->SetOrientation(&q);
		}
		else
		{
			m_Tracking = true;
			m_RenderObj.GetFrame(0)->GetOrientation(&m_Q0);
			m_Q1 = m_Q0;
			m_Velocity = 120.0f;
			m_LastUpdate = g_time - m_UpdatePeriod;
		}
	}
	else
	{
		if (m_Target)
		{
			if (m_Target->IsActive())
			{
				t = g_time - m_LastUpdate;

				if (t >= m_UpdatePeriod)
				{
					CVector3f oldfwd, newfwd, tpos, pos, lead(0.0f, 0.0f, 0.0f);

					m_Q0 = m_Q1;

					// Find new orientation, lead target a little
					m_RenderObj.GetFrame(0)->GetForward(&oldfwd);
					m_Target->GetPosition(&tpos, 0);
					m_Target->GetVelocity(&lead);
					Vec3fScale(&lead, &lead, m_UpdatePeriod);
					Vec3fAdd(&tpos, &tpos, &lead);
					GetPosition(&pos, 0);
					Vec3fSubtract(&newfwd, &tpos, &pos);
					Vec3fNormalize(&newfwd, &newfwd);

					QuatRotationArc(&q, &oldfwd, &newfwd);
					QuatCrossProduct(&m_Q1, &q, &m_Q1);

					m_LastUpdate += m_UpdatePeriod;
					t = g_time - m_LastUpdate;
				}

				QuatSlerp(&q, &m_Q0, &m_Q1, t * m_SlerpScale);
				m_RenderObj.GetFrame(0)->SetOrientation(&q);
			}
			else
				m_Target = 0;
		}
	}

   // Move the shot forward
   MoveForward(m_Velocity * g_FrameTime, 0);

   // Update the ambient sound
   GetPosition(&m_CurPosition, 0);
   CVector3f Velocity;
   Velocity.x = (m_CurPosition.x - m_LastPosition.x) / g_FrameTime;
   Velocity.y = (m_CurPosition.y - m_LastPosition.y) / g_FrameTime;
   Velocity.z = (m_CurPosition.z - m_LastPosition.z) / g_FrameTime;
   m_MissileInAir->UpdateSound(m_CurPosition, Velocity);
   m_LastPosition = m_CurPosition;

   CGameObject::Update();
}