Exemplo n.º 1
0
float GetAngle( Vector3 &a, Vector3 &b )
{
	float lengthA = a.GetLength();
	float lengthB = b.GetLength();
	float dot = DotProduct( a, b );

	return acos( dot / (lengthA * lengthB) );
}
Exemplo n.º 2
0
		void Corpse::Spring(NodeType n1,
							NodeType n2,
							float distance,
							float dt){
			SPADES_MARK_FUNCTION_DEBUG();
			SPAssert(n1 >= 0); SPAssert(n1 < NodeCount);
			SPAssert(n2 >= 0); SPAssert(n2 < NodeCount);
			Node& a = nodes[n1];
			Node& b = nodes[n2];
			Vector3 diff = b.pos - a.pos;
			float dist = diff.GetLength();
			Vector3 force = diff.Normalize() * (distance - dist);
			force *= dt * 50.f;
			
			b.vel += force;
			a.vel -= force;
			
			b.pos += force / (dt * 50.f) * 0.5f;
			a.pos -= force / (dt * 50.f) * 0.5f;
			
			Vector3 velMid = (a.vel + b.vel) * .5f;
			float dump = 1.f - powf(.1f, dt);
			a.vel += (velMid - a.vel) * dump;
			b.vel += (velMid - b.vel) * dump;
			
		}
Exemplo n.º 3
0
		void Corpse::Spring(NodeType n1a,
							NodeType n1b,
							 NodeType n2,
							 float distance,
							 float dt){
			SPADES_MARK_FUNCTION_DEBUG();
			SPAssert(n1a >= 0); SPAssert(n1a < NodeCount);
			SPAssert(n1b >= 0); SPAssert(n1b < NodeCount);
			SPAssert(n2 >= 0); SPAssert(n2 < NodeCount);
			Node& x = nodes[n1a];
			Node& y = nodes[n1b];
			Node& b = nodes[n2];
			Vector3 diff = b.pos - (x.pos + y.pos) * .5f;
			float dist = diff.GetLength();
			Vector3 force = diff.Normalize() * (distance - dist);
			force *= dt * 50.f;
			
			b.vel += force;
			force *= .5f;
			x.vel -= force;
			y.vel -= force;
			
			Vector3 velMid = (x.vel + y.vel) * .25f + b.vel * .5f;
			float dump = 1.f - powf(.05f, dt);
			x.vel += (velMid - x.vel) * dump;
			y.vel += (velMid - y.vel) * dump;
			b.vel += (velMid - b.vel) * dump;
			
		}
Exemplo n.º 4
0
		void Corpse::AngleSpring(NodeType n1id,
								 NodeType n2id,
								 Vector3 dir,
								 float minDot,
								 float maxDot,
								 float dt){
			Node& n1 = nodes[n1id];
			Node& n2 = nodes[n2id];
			Vector3 diff = n2.pos - n1.pos;
			float ln1 = diff.GetLength();
			float dot = Vector3::Dot(diff, dir) / (ln1 + 0.000000001f);
			
			if(dot >= minDot && dot <= maxDot)
				return;
			
			float strength = 0.f;
			
			Vector3 a1 = Vector3::Cross(dir, diff);
			a1 = Vector3::Cross(diff, a1).Normalize();
			
			Vector3 a2 = -a1;
			//a1=-a1; a2=-a2;
			//a1 = -a1;
			
			if(dot > maxDot){
				strength = MyACos(dot) - MyACos(maxDot);
			}else if(dot < minDot){
				strength = MyACos(dot) - MyACos(minDot);
			}
			
			SPAssert(!isnan(strength));
			
			strength *= 100.f;
			strength *= dt;
			
			a1 *= strength;
			a2 *= strength;
			
			n2.vel += a1;
			n1.vel += a2;
			//nBase.vel -= a1 + a2;
			
			/*
			 d1 += a1 * 0.01;
			 d2 += a2 * 0.01;
			 float nd = Vector3::Dot(d1, d2) / (d1.GetLength() * d2.GetLength());
			 
			 if(dot > maxDot){
			 if(nd < dot)
			 printf("GOOD %f -> %f\n", dot, nd);
			 else
			 printf("BAD %f -> %f\n", dot, nd);
			 }else{
			 if(nd > dot)
			 printf("GOOD %f -> %f\n", dot, nd);
			 else
			 printf("BAD %f -> %f\n", dot, nd);
			 }*/
		}
Exemplo n.º 5
0
/**
*  @brief
*    Called when the scene node needs to be updated
*/
void PGSparkles::OnUpdate()
{
	// If this scene node wasn't drawn at the last frame, we can skip some update stuff
	if ((GetFlags() & ForceUpdate) || m_bUpdate) {
		m_bUpdate = true;

		// If there are free particles, create new particles
		if (!(System::GetInstance()->GetMicroseconds() % BuildPerSec)) {
			while (Math::GetRand() % 5) {
				Particle *pParticle = AddParticle();
				if (pParticle)
					InitParticle(*pParticle);
				else
					break;
			}
		}

		{ // Update particles
			float fTimeDiff = Timing::GetInstance()->GetTimeDifference();
			Iterator<Particle> cIterator = GetParticleIterator();
			while (cIterator.HasNext()) {
				Particle &cParticle = cIterator.Next();

				// Update velocity
				cParticle.vVelocity += GetGravity()*fTimeDiff*(200-cParticle.fEnergy)/10;
				cParticle.vVelocity -= cParticle.vVelocity*fTimeDiff;

				// Self induction to make the sparkles a bit more interesting ;-)
				if (!(System::GetInstance()->GetMicroseconds() % 500) && !(Math::GetRand() % 5)) {
					cParticle.fEnergy += 100;
					cParticle.fSize   += 0.2f;
				}

				// Update position
				Vector3 vMove = cParticle.vVelocity*fTimeDiff*cParticle.fEnergy/100;
				cParticle.vPos += vMove/10;

				// Update distortion
				cParticle.fCustom1 += fTimeDiff;
				float dLength = cParticle.fCustom1/vMove.GetLength()*5;
				cParticle.vDistortion = vMove*dLength;

				// Update energy, size and lifetime
				cParticle.fEnergy -= fTimeDiff*EnergyPerSec;
				cParticle.fSize   -= fTimeDiff;
				if (cParticle.fEnergy <= 0 || cParticle.fSize <= 0)
					InitParticle(cParticle);
				else
					cParticle.vColor[3] = cParticle.fEnergy/255;
			}
		}

		// We have to recalculate the current axis align bounding box in 'scene node space'
		DirtyAABoundingBox();
	}
}
Exemplo n.º 6
0
//! returns the closest point on a line segment [A B]
Vector3 Math::GetClosestPointOnLine(const Vector3& vPoint, const Vector3& vA, const Vector3& vB)
{
    Vector3 vC = vPoint-vA;
    Vector3 vD = vB-vA;
    float fLength = vD.GetLength();

    vD = vD / fLength;
    float t = vD.DotProduct(vC);

    if(t < 0.0f)
    {
        return vA;
    }
    else if(t > fLength)
    {
        return vB;
    }

    return vA + vD*t;
}
Exemplo n.º 7
0
	const F32 FreetypeFont::Measure(const std::string & text, const Vector3<F32> & forward)
	{
		F32 length = 0.0f;

		for(auto it = text.begin(); it != text.end(); ++it)
		{
			char c = *it;

			if(FT_Load_Char(m_FontFace, c, FT_LOAD_RENDER))
			{
				LOG("could not load character, " << c);
			}

			FT_GlyphSlot g = m_FontFace->glyph;

			length += static_cast<F32>(g->advance.x >> 6) * m_ResolutionScale.x();
		}

		return length * forward.GetLength();
	}
	//! 3D sphere vs ray intersection check
	bool CollisionUtils::SphereIntersectsWithRay(const Vector3& vCenter, f32 fRadius, const Vector3& vRayStart, const Vector3& vRayDir, f32* fRayLength /*= 0*/, f32* fDistToIntersection /*= 0*/)
	{
		Vector3 vToSphere = vCenter-vRayStart;
		f32 fDist = vToSphere.GetLength();
		f32 fV = vToSphere.DotProduct(vRayDir);
		f32 fD = fRadius*fRadius - (fDist*fDist - fV*fV);
		f32 _fDistToIntersection = fV - Math::SquareRoot(fD);

		if(fD < 0.0f || _fDistToIntersection < 0.0f)
		{
			return false;
		}
		
		if(fRayLength && (*fRayLength < _fDistToIntersection))
		{
			return false;
		}

		if(fDistToIntersection)
		{
			*fDistToIntersection = _fDistToIntersection;
		}
		return true;
	}
Exemplo n.º 9
0
void PhysicsEngine::CollisionSphereResponse(PowerBall* b, PowerBall* b1)
{
	// normal of the "collision plane"
	//Vector3 nColl = this->GetPositionVector3() - b1->GetPositionVector3();
	Vector3 nColl = b->GetTempPosition() - b1->GetTempPosition();
	// for easy projecting of vector, no div by |n|^2 in proj formula
	Vector3 tempa = nColl;
	nColl.normalize();

	// savning the important stuff for easy acc
	float m1 = b->GetMass();
	float m2 = b1->GetMass();
	float mSum = m1+m2;
	Vector3 v1 = b->GetVelocity();
	Vector3 v2 = b1->GetVelocity();

	// projecting the vector v1 on nColl
	float x1 = nColl.GetDotProduct(v1);		// factor in nColl dir
	Vector3 v1x = nColl*x1;					// projetion done
	Vector3 v1y = v1 - v1x;					// perpendicular vector 

	// projecting the vector v2 on nColl
	nColl = nColl*(-1);						// switching direction of "plane normal"
	float x2 = nColl.GetDotProduct(v2);		// factor in nColl dir
	Vector3 v2x = nColl*x2;					// projetion done
	Vector3 v2y = v2 - v2x;					// perpendicular vector 

	float e1 = b->GetRestitution();
	float e2 = b1->GetRestitution();
	float e = (e1 + e2)/2.0f;

	if(((v1x-v2x).GetLength() > 0.6f) && b->SoundEnabled())
		this->mCollisionWithBall->Play();
	

	/*
	this->mVelocity = Vector3( v1x*(m1-m2)/(mSum) + v2x*(2*m2)/(mSum) + v1y );
	b1->mVelocity = Vector3( v1x*(2*m1)/(mSum) + v2x*(m2-m1)/(mSum) + v2y );
	*/
	b->SetVelocity(Vector3( v1x*(m1-m2*e)/(mSum) + v2x*((1+e)*m2)/(mSum) + v1y ));
	b1->SetVelocity(Vector3( v1x*((1+e)*m1)/(mSum) + v2x*(m2-m1*e)/(mSum) + v2y ));

	
	/* calculating damage. */
	if(b->WarlockMode())
	{
		Vector3 ve1 = b->GetVelocity();
		Vector3 ve2 = b1->GetVelocity();
		Vector3 relativeV = ve1 - ve2;
		if( relativeV.GetLength() > 0.6f)
		{
			float v1 = ve1.GetLength();
			float v2 = ve2.GetLength();
			float mass1 = b->GetMass();
			float mass2 = b1->GetMass();
			float momentum1 = v1 * mass1;
			float momentum2 = v2 * mass2;
			float sumMomentum = momentum1 + momentum2;
			/* to make it clear. if ball 1 has the speed of 10 m/s and ball 2 has
			** the speed 0 m/s, ball 1 will not get any damage but ball 2 gets
			** his health minus 10* (10 / 10) = 10 so ball 2 has lost 10 in hp.
			** this works good because we using momentum as a weighted value. 
			*/
			float damage1 = 10.0f* (momentum2 / sumMomentum); 
			float damage2 = 10.0f* (momentum1 / sumMomentum);
			float health1 = b->GetHealth();
			health1 -= damage1;
			b->SetHealth(health1);
			float health2 = b1->GetHealth();
			health2 -= damage2;
			b1->SetHealth(health2);
		}
	}
	
	/* informing the spells to the balls that it has been a collision */
	Spell** spells = b->GetSpells();
	for(int i = 0;i<b->GetNrOfSpells();i++)
		spells[i]->InformCollision();
	spells = b1->GetSpells();
	for(int i = 0;i<b1->GetNrOfSpells();i++)
		spells[i]->InformCollision();

}
Exemplo n.º 10
0
bool PhysicsEngine::CollisionWithSphereSimple(PowerBall* b, PowerBall* b1)
{
	Vector3 r = b->GetPositionVector3() - b1->GetPositionVector3();
	r = b->GetTempPosition() - b1->GetTempPosition();

	float distanceBalls = r.GetLength();
	float sumRadius = b->GetRadius() + b1->GetRadius();
	if(distanceBalls > sumRadius)
		return false;

	/*  we have collision but we need to move the balls so they are not inside each other
	*	solve this equation: ((pos1 - t*vel1) - (pos2 - t*vel2)).length = radie1 + radie2
	*
	*	this gives ut the following:
	*	d	 = distance = p1-p2
	*	rV	 = relative velocity = v2-v1
	*	sumR = sumRadius = r1 + r2 
	*
	*	t    = - rV.dot(d)/|rV|^2 +- sqrt( rV.dot(d)^2/|rV|^4 - (sumR^2 - |d|^2) / |rV|^2
	*
	*/
	Vector3 d = b->GetPositionVector3() - b1->GetPositionVector3();
	d = b->GetTempPosition() - b1->GetTempPosition();

	Vector3 rV = b1->GetVelocity() - b->GetVelocity();
	float sumR = b->GetRadius() + b1->GetRadius();
	float tempA = rV.GetDotProduct(d) / rV.GetLengthSquared();
	float tempB = tempA*tempA;
	float tempC = (d.GetLengthSquared() - sumR*sumR) / rV.GetLengthSquared();
	float tempSq = tempB - tempC;
	if( tempSq < 0) // no real solutions
		return false;
	else
	{
		float t1 = - tempA - sqrt(tempSq);
		float t2 = - tempA + sqrt(tempSq);
		Vector3 newPos1, newPos2;
		if(t1 >= 0)
		{
			/*
			newPos1 = this->GetPositionVector3() - this->mVelocity*t1;
			newPos2 = b1->GetPositionVector3() - b1->mVelocity*t1;
								
			this->SetPosition(newPos1);
			b1->SetPosition(newPos2);
			*/

			newPos1 = b->GetTempPosition() - b->GetVelocity()*t1;
			newPos2 = b1->GetTempPosition() - b1->GetVelocity()*t1;
			b->SetTempPosition(newPos1);
			b1->SetTempPosition(newPos2);
		}
		else if(t2 >= 0)
		{
			/*
			newPos1 = this->GetPositionVector3() - this->mVelocity*t2;
			newPos2 = b1->GetPositionVector3() - b1->mVelocity*t2;
			
			this->SetPosition(newPos1);
			b1->SetPosition(newPos2);
			*/
			newPos1 = b->GetTempPosition() - b->GetVelocity()*t2;
			newPos2 = b1->GetTempPosition() - b1->GetVelocity()*t2;
			b->SetTempPosition(newPos1);
			b1->SetTempPosition(newPos2);
		}
		else 
			return false;
	}
	return true;
}
Exemplo n.º 11
0
float Vector3::AngleWith(const Vector3 &vec) const {
    return (float)acos( DotProduct(vec))/(GetLength() * vec.GetLength());
}
Exemplo n.º 12
0
void Game::PlayGameMode2()
{
	GraphicsEngine* mGe = GetGraphics();
	
	GetGraphics()->ShowLoadingScreen("Media/LoadingScreen/LoadingScreenBG2.png", "Media/LoadingScreen/LoadingScreenPB.png", 1.0f, 1.0f);
	GetGraphics()->ChangeSkyBox("Media/StarMap.dds"); 

	GetGraphics()->GetCamera()->SetUpVector(Vector3(0, 1, 0));
	GetGraphics()->GetCamera()->SetForward(Vector3(1, 0, 0));
	GetGraphics()->GetCamera()->SetPosition(Vector3(-17.0f, 56.0f, 0));
	GetGraphics()->GetCamera()->LookAt(GetGraphics()->GetCamera()->GetPosition() - Vector3(1, 0.3f, 0));

	iLight* mLights[5];
	mLights[0] = mGe->CreateLight(Vector3(0, 50, 0));
	mLights[1] = mGe->CreateLight(Vector3(0, 50, -20)); 
	mLights[2] = mGe->CreateLight(Vector3(0, 50, 20));
	mLights[3] = mGe->CreateLight(Vector3(10, 50, 0));
	mLights[4] = mGe->CreateLight(Vector3(-10, 50, 0));
	for(int i = 0; i < 5; i++)
		mLights[i]->SetIntensity(30.0f);

	GetGraphics()->SetSunLightDisabled();
	GetGraphics()->SetSceneAmbientLight(Vector3(0.4f, 0.4f, 0.4f));

	Vector3 centerPlatform = Vector3(0,20,0);
	Map* mPlatform = new Map("Media/MazeMapFixed.obj", centerPlatform);
	Map* mBox = new Map("Media/MazeMapFrame.obj", centerPlatform + Vector3(0,1,0) );
	mPlatform->SetShrinkValue(0.0f);

	/* set so we cant tilt it more than these angles. */
	mPlatform->SetMaxAngleX(10.0f*(PI/180.0f));
	mPlatform->SetMaxAngleZ(10.0f*(PI/180.0f));
	mPlatform->SetRotate(false);
	mPlatform->SetTargetAngleX(0.5f);
	mPlatform->SetTargetAngleZ(-0.5f);

	PowerBall* mBalls = new PowerBall("Media/Ball.obj", START_POS);
	mBalls->SetForwardVector(Vector3(0,0,1));
	mBalls->SetKnockoutMode();
	mBalls->SetAcceleration(mBalls->GetAcceleration()*30.0f);


	iText* timeTxt = GetGraphics()->CreateText("", Vector2(50, 60), 1.0f, "Media/fonts/new");
	iText* scoreTxt = GetGraphics()->CreateText("", Vector2(50, 95), 1.0f, "Media/fonts/new");

	iImage* guiStar = GetGraphics()->CreateImage(Vector2(200, 90), Vector2(75, 75), "Media/star.png");
	guiStar->SetOpacity(0.0f);
	float starTimer = 0.0f;


	GetGraphics()->LoadingScreen("Media/LoadingScreen/LoadingScreenBG2.png", "Media/LoadingScreen/LoadingScreenPB.png", 1.0f, 1.0f, 1.0f, 1.0f);
	this->FlushQueue();

	mGe->GetCamera()->SetPosition(centerPlatform + Vector3(0.0f, 30.0f, 20.0f));
	mGe->GetCamera()->LookAt(centerPlatform);

	// Score / results:
	float time = 0.0f;
	bool started = false;
	int score = 0;

	float delayTimer = 1000.0f;

	GetGraphics()->GetKeyListener()->SetCursorVisibility(false);

	go = true;
	const Vector3 DefaultDir = Vector3(0.0f, 1.0f, 0.0f);
	int currentPrev = 0;
	Vector3 prevVectors[NROFPREV];
	for(int i = 0; i < NROFPREV; i++)
	{
		prevVectors[i] = DefaultDir;
	}

	while(delayTimer > 0)
	{
		float diff = GetGraphics()->Update();
		delayTimer -= diff;
	}

	while(GetGraphics()->IsRunning() && go)
	{
		if(mGe->GetKeyListener()->IsPressed('1'))
		{
			mGe->GetCamera()->SetPosition(centerPlatform+ Vector3(20.0f, 30.0f, 20.0f));
			mGe->GetCamera()->LookAt(centerPlatform );
		}
		if(mGe->GetKeyListener()->IsPressed('2'))
		{
			mGe->GetCamera()->SetPosition(centerPlatform+ Vector3(20.0f, 30.0f, -20.0f));
			mGe->GetCamera()->LookAt(centerPlatform );
		}
		if(mGe->GetKeyListener()->IsPressed('3'))
		{
			mGe->GetCamera()->SetPosition(centerPlatform+ Vector3(-20.0f, 30.0f, 20.0f));
			mGe->GetCamera()->LookAt(centerPlatform );
		}
		if(mGe->GetKeyListener()->IsPressed('4'))
		{
			mGe->GetCamera()->SetPosition(centerPlatform+ Vector3(-20.0f, 30.0f, -20.0f));
			mGe->GetCamera()->LookAt(centerPlatform );
		}

		// Updates GFX
		float diff = GetGraphics()->Update();

		// Handle events such as network packets and client connections
		this->HandleEvent(diff);
	
		if(GetGraphics()->GetKeyListener()->IsPressed(VK_ESCAPE))
			go = false;
		if(GetGraphics()->GetKeyListener()->IsPressed('R') || (this->networkController != NULL && this->networkController->needRestart == true))
		{
			if(this->networkController != NULL)
			{
				this->networkController->needRestart = false;
			}
			delete mBalls;

			// Spawn at last score - 1;
			if(score == 0)
				mBalls = new PowerBall("Media/Ball.obj", scorePos[0]);
			else
				mBalls = new PowerBall("Media/Ball.obj", scorePos[score - 1]);

			mBalls->SetForwardVector(Vector3(0,0,1));
			mBalls->SetKnockoutMode();
			mBalls->SetAcceleration(mBalls->GetAcceleration()*15.0f);

			mPlatform->ResetXZAngles();
			mPlatform->RotateX(0);
		}
		iPhysicsEngine* pe = GetGraphics()->GetPhysicsEngine();
		mBalls->UpdateBallParentMode(mPlatform);
		mBalls->Update(diff);
		Vector3 normalPlane;
		if(pe->DoSpecialPhoneCollisionGame(mBalls, mPlatform, normalPlane, diff))
			mBalls->collisionPlatformResponse(mPlatform, normalPlane, diff);
		mBalls->UpdatePost();
		mPlatform->Update(diff);

		if(this->networkController)
		{
			mPlatform->SetRotate(true);
			Vector3 phoneDirr = Vector3(this->networkController->direction.y, this->networkController->direction.z, -this->networkController->direction.x);
			//Vector3 phoneDirr = this->networkController->direction;
			phoneDirr.Normalize();
			prevVectors[currentPrev] = phoneDirr;
			float angle = CalcAngle(phoneDirr, DefaultDir, prevVectors, currentPrev);

			float angleX = acos(DefaultDir.GetDotProduct(Vector3(0, phoneDirr.y , phoneDirr.z).Normalize()));
			float angleZ = acos(DefaultDir.GetDotProduct(Vector3(phoneDirr.x, phoneDirr.y, 0).Normalize()));
			if(phoneDirr.z > 0)
			{
				angleX *= -1;
			}
			if(phoneDirr.x < 0)
			{
				angleZ *= -1;
			}
			mPlatform->SetTargetAngleX(angleX/4);
			mPlatform->SetTargetAngleZ(angleZ/4);

			angle /= 4;
			currentPrev++;
			if(currentPrev >= NROFPREV)
				currentPrev = 0;
		}
		if(mGe->GetKeyListener()->IsPressed('W'))
		{
			mPlatform->RotateX(-diff);

			Vector3 tempPos = mBalls->GetPosition() - mPlatform->GetMesh()->GetPosition();
			tempPos.RotateAroundAxis(Vector3(1,0,0), (PI/8.0f)*-diff*0.001f);
			mBalls->SetPosition(mPlatform->GetMesh()->GetPosition() + tempPos);
		}
		if(mGe->GetKeyListener()->IsPressed('S'))
		{
			mPlatform->RotateX(diff);

			Vector3 tempPos = mBalls->GetPosition() - mPlatform->GetMesh()->GetPosition();
			tempPos.RotateAroundAxis(Vector3(1,0,0), (PI/8.0f)*diff*0.001f);
			mBalls->SetPosition(mPlatform->GetMesh()->GetPosition() + tempPos);
		}
		if(mGe->GetKeyListener()->IsPressed('A'))
		{
			mPlatform->RotateZ(-diff);

			Vector3 tempPos = mBalls->GetPosition() - mPlatform->GetMesh()->GetPosition();
			tempPos.RotateAroundAxis(Vector3(0,0,1), (PI/8.0f)*-diff*0.001f);
			mBalls->SetPosition(mPlatform->GetMesh()->GetPosition() + tempPos);
		}
		if(mGe->GetKeyListener()->IsPressed('D'))
		{
			mPlatform->RotateZ(diff);

			Vector3 tempPos = mBalls->GetPosition() - mPlatform->GetMesh()->GetPosition();
			tempPos.RotateAroundAxis(Vector3(0,0,1), (PI/8.0f)*diff*0.001f);
			mBalls->SetPosition(mPlatform->GetMesh()->GetPosition() + tempPos);
		}
		
		//////////////////////////////////////////////////////////////////////////
		static bool posb = true;
		if(GetGraphics()->GetKeyListener()->IsPressed('Q'))
		{
			if(posb)
			{
				MaloW::Debug(mBalls->GetPosition());
				posb = false;
			}			
		}
		else
			posb = true;
		//////////////////////////////////////////////////////////////////////////

		if(started)
		{
			for(int i = score + 1; i < 15; i++)
			{
				Vector3 toScore = scorePos[i] - mBalls->GetPosition();
				toScore.y = 0.0f;
				float distanceToScore = toScore.GetLength();
				if(distanceToScore < 2.0f)
				{
					score = i;
					starTimer = 2.0f;

					// Do Vibration
					if(this->networkController)
					{
						this->networkController->cc->sendData("VIB: 100");
					}
				}
			}

			time += diff * 0.001f;
		}
		else
		{
			if((mBalls->GetPosition() - Vector3(-13.0f,25,-13)).GetLength() > 3)
			{
				started = true;
			}
		}

		starTimer -= diff * 0.001f;
		if(starTimer < 0.0f)
			starTimer = 0.0f;
		guiStar->SetOpacity(starTimer);

		// print score and time text
		scoreTxt->SetText(string("SCORE: " + MaloW::convertNrToString(score)).c_str());
		timeTxt->SetText(string("TIME: " + MaloW::convertNrToString(time)).c_str());


		// End game after 2 mins
		if(time > 120.0f || score > 13)
		{
			this->FinishScreen(score, "2, Labyrinth", time);
			go = false;
		}
	}

	if(this->networkController)
	{
		this->networkController->cc->sendData("QUITTING");
	}

	for(int i = 0; i < 5; i++)
		mGe->DeleteLight(mLights[i]);

	delete mPlatform;
	delete mBalls;
	delete mBox;

	mGe->DeleteText(timeTxt);
	mGe->DeleteText(scoreTxt);
	GetGraphics()->DeleteImage(guiStar);
}
Exemplo n.º 13
0
bool Warlock::checkWinConditions(float dt)
{
	float newdt = dt/1000.0f;

	this->mTimeElapsed += newdt;
	Vector3 pos;
	Vector3 posLav;
	float distance = -1;
	int numberBallsAlive = 0;
	for(int i = 0; i<this->mNumberOfPlayers; i++)
	{
		pos = this->mBalls[i]->GetPositionVector3();
		posLav = Vector3(pos.x,this->mGe->GetLavaHeightAt(pos.x, pos.z), pos.z);
		Vector3 distanceVector = (pos - posLav);
		distance = distanceVector.GetLength();
		if(distance < this->mBalls[i]->GetRadius() ||  distanceVector.y < 0.0f )
		{
			/* here the ball take damage. */
			float radiusMapInside = 55.0f;
			float moreDamageDistance = pos.GetLength() - radiusMapInside;
			moreDamageDistance *= 0.5f;
			/* minus 4 hp per sec and minus distance in lava per sec */
			this->mBalls[i]->SetHealth(this->mBalls[i]->GetHealth() - 4.0f*newdt - moreDamageDistance*newdt);
		}
	}
	/*
	if(this->mTimeElapsed > 600.0f)
		return true;
	return false;*/
	int ballIndex = 0;
	int* arrayIndexs = new int[this->mNumberOfPlayers];
	bool returnValue = false;
	
	/* checking which balls that are alive. */
	for(int i = 0; i<this->mNumberOfPlayers; i++)
	{
		if(this->mBalls[i]->GetHealth() > 0)
		{
			/* saving the index of the balls that are alive and how many they are. */
			arrayIndexs[numberBallsAlive] = i;
			numberBallsAlive++;
		}
	}

	/* checking so they belong to the same team. */
	int numberRed = 0;
	int numberBlue = 0;
	int numberNone = 0;
	
	for(int i = 0; i<numberBallsAlive; i++)
	{
		ballIndex = arrayIndexs[i];
		if(this->mBalls[ballIndex]->GetTeam() == TEAM::BLUETEAM)
			numberBlue++;
		if(this->mBalls[ballIndex]->GetTeam() == TEAM::REDTEAM)
			numberRed++;
		if(this->mBalls[ballIndex]->GetTeam() == TEAM::NOTEAM) // this is for free 4 all
			numberNone++;
	}
	/* if all balls belong to the same team and they are more that zero alive on the map or one alive in free 4 all. */
	if((numberBallsAlive >0) && (numberBallsAlive == numberBlue || numberBallsAlive == numberRed || numberNone == 1 ))  
	{
		/* here the round is over. */
		/* to do. add winning information to teams or to player in free 4 all. */
		returnValue = true;
	}	
	else
	{
		returnValue = false;
	}
	delete arrayIndexs;

	
	/* when someone starts a game there will only be one alive on the map and he will be the winner by algoritm
	** but for free 4 all it has to be at least 2 players for the win condition to be able to be true.
	** and at least one player for each team in team mode of warlock for the win condition to be able to be true.
	** 
	*/

	/* checking which ball belong to which team and how many they are and how many that are no team aka free 4 all. */
	numberRed = 0;
	numberBlue = 0;
	numberNone = 0;
	
	for(int i = 0; i<this->mNumberOfPlayers; i++)
	{
		if(this->mBalls[i]->GetTeam() == TEAM::BLUETEAM)
			numberBlue++;
		if(this->mBalls[i]->GetTeam() == TEAM::REDTEAM)
			numberRed++;
		if(this->mBalls[i]->GetTeam() == TEAM::NOTEAM) // this is for free 4 all
			numberNone++;
	}
	
	if(returnValue && ( (numberRed > 0 && numberBlue > 0) || numberNone > 1))
	{
		for(int i = 0; i<this->mNumberOfPlayers; i++)
		{
			this->mBalls[i]->ResetTime();
			this->mBalls[i]->SetToStartPosition();
			this->mBalls[i]->SetForwardVector(this->mNet->GetBall(i)->GetStartForwardVector());
			this->mNet->GetBall(i)->SetPos(this->mBalls[i]->GetPosition());
			Vector3 vel = Vector3(0,0,0);
			this->mNet->GetBall(i)->SetVel(::D3DXVECTOR3(vel.x, vel.y, vel.z));
			this->mNet->GetBall(i)->SetForwardVector(this->mNet->GetBall(i)->GetStartForwardVector());
		}
		returnValue = true;
	}
	else
		returnValue = false;
	return returnValue;
	
}
Exemplo n.º 14
0
const float Vector3::GetDistance(const Vector3& v) const
{
	const Vector3 d(v.x - x, v.y - y, v.z - z);
	return d.GetLength();
}
Exemplo n.º 15
0
bool PhysicsEngine::CollisionWithMapSimple(PowerBall* b, Map* map, Vector3 &normalPlane)
{
	
	MaloW::Array<MeshStrip*>* temp = map->GetMesh()->GetStrips();
	//int sizeMstrip = temp->size();
	int sizeVertexS0 = temp->get(0)->getNrOfVerts();
	Vertex* verts;
	//Vector3 origin = this->GetPositionVector3();
	Vector3 origin = b->GetTempPosition();
	Vector3 dir = b->GetVelocity();
	Vector3 dirN = dir/dir.GetLength();
	verts = temp->get(0)->getVerts();
	/*
	for(int i = 0;i<sizeMstrip;i++)
	{
		
	}
	*/
	Vector3 p0,p1,p2, normal, v1,v2;
	float smalestTime = -1;
	bool firstHit = false;
	float u, v,t;
	float lengthProjN = 0;
	Vector3 p0Store, p1Store,p2Store, normalStore;
	Vector3 pos = Vector3(map->GetMesh()->GetPosition());
	Vector3 posS = b->GetTempPosition();//this->GetPositionVector3();
	Vector3 rayDirection;
	Vector3 scalingMesh = map->GetMesh()->GetScaling();

	D3DXMATRIX quat;
	D3DXMatrixRotationQuaternion(&quat, &map->GetMesh()->GetRotation()); 
	Matrix4 rotate(quat);
	rotate.TransposeThis();

	Matrix4 scaling;
	scaling.SetScale(scalingMesh);

	Matrix4 translate;
	translate.SetTranslate(pos);
	
	Matrix4 world = translate*rotate*scaling;
	
	for(int i =0; i< sizeVertexS0; i+=3)
	{
		
		/*
		p0 = Vector3(verts[i].pos).GetComponentMultiplication(scalingMesh) + pos;
		p1 = Vector3(verts[i+1].pos).GetComponentMultiplication(scalingMesh) +pos;
		p2 = Vector3(verts[i+2].pos).GetComponentMultiplication(scalingMesh) + pos;
		*/
		p0 = world*Vector3(verts[i].pos);
		p1 = world*Vector3(verts[i+1].pos);
		p2 = world*Vector3(verts[i+2].pos);

		v1 = p1-p0;
		v2 = p2-p0;
		rayDirection = v1.GetCrossProduct(v2);
		rayDirection.normalize();
		float tempLength;
		Vector3 ny;
		Vector3 projN;
		if(RayTriIntersect(origin , rayDirection, p0, p1, p2, u, v, t) )
		{
			normal = rayDirection;
			ny = origin - p0;
			projN = normal*ny.GetDotProduct(normal);
			tempLength = projN.GetLength();
			if(!firstHit)
			{
				firstHit = true;
				smalestTime = t;
				lengthProjN = tempLength;
				p0Store = p0;
				p1Store = p1;
				p2Store = p2;
				normalStore = normal;
			}
			else
			{
				if( tempLength < lengthProjN )
				{
					smalestTime = t;
					lengthProjN = tempLength;
					p0Store = p0;
					p1Store = p1;
					p2Store = p2;
					normalStore = normal;
				}
			}			
		}
		// check agains all edges
		Vector3 lineDirection;
		float scalarProj;
		Vector3 projOnLine;
		Vector3 normalToLine;
		// edge 1:
		ny = origin - p0;
		lineDirection = p1 - p0;
		scalarProj = (ny.GetDotProduct(lineDirection)/lineDirection.GetLengthSquared());
		projOnLine = lineDirection * scalarProj;
		if( (scalarProj >= 0.0f) && (scalarProj <= 1) )
		{
			normalToLine = ny - projOnLine;
			tempLength = normalToLine.GetLength();
			if(!firstHit)
			{
				firstHit = true;
				lengthProjN = tempLength;
				p0Store = p0;
				p1Store = p1;
				p2Store = p2;
				normalStore = normalToLine;
				normalStore.normalize();
			}
			else
			{
				if( tempLength < lengthProjN )
				{
					lengthProjN = tempLength;
					p0Store = p0;
					p1Store = p1;
					p2Store = p2;
					normalStore = normalToLine;
					normalStore.normalize();
				}
			}	

		}
		// edge 2:
		ny = origin - p1;
		lineDirection = p2 - p1;
		scalarProj = (ny.GetDotProduct(lineDirection)/lineDirection.GetLengthSquared());
		projOnLine = lineDirection * scalarProj;
		if( (scalarProj >= 0.0f) && (scalarProj <= 1) )
		{
			normalToLine = ny - projOnLine;
			tempLength = normalToLine.GetLength();
			if(!firstHit)
			{
				firstHit = true;
				lengthProjN = tempLength;
				p0Store = p0;
				p1Store = p1;
				p2Store = p2;
				normalStore = normalToLine;
				normalStore.normalize();
			}
			else
			{
				if( tempLength < lengthProjN )
				{
					lengthProjN = tempLength;
					p0Store = p0;
					p1Store = p1;
					p2Store = p2;
					normalStore = normalToLine;
					normalStore.normalize();
				}
			}	

		}
		// edge 3:
		ny = origin - p2;
		lineDirection = p0 - p2;
		scalarProj = (ny.GetDotProduct(lineDirection)/lineDirection.GetLengthSquared());
		projOnLine = lineDirection * scalarProj;
		if( (scalarProj >= 0.0f) && (scalarProj <= 1) )
		{
			normalToLine = ny - projOnLine;
			tempLength = normalToLine.GetLength();
			if(!firstHit)
			{
				firstHit = true;
				lengthProjN = tempLength;
				p0Store = p0;
				p1Store = p1;
				p2Store = p2;
				normalStore = normalToLine;
				normalStore.normalize();
			}
			else
			{
				if( tempLength < lengthProjN )
				{
					lengthProjN = tempLength;
					p0Store = p0;
					p1Store = p1;
					p2Store = p2;
					normalStore = normal;
				}
			}	

		}
	}
	if(firstHit)
	{
		// for checking if the ball are in the air not turned on at the moment, 
		float eps = 0.5f; //0.001
		if( (lengthProjN < (b->GetRadius() + eps)) && (lengthProjN > (b->GetRadius() - eps)) )
		{
			b->SetNormalContact(normalStore);
			b->SetHasContact(true);
		}
		else 
		{
			b->SetNormalContact(normalStore);
			b->SetHasContact(false);
		}

		if( lengthProjN <= b->GetRadius())
		{
			Vector3 velNorm = b->GetVelocity();
			velNorm.normalize();
			
			if(normalStore.GetDotProduct(velNorm) >=0)
				return false;
	
			float diff = abs(lengthProjN- b->GetRadius());
			
			//Vector3 newPo = origin -dirN*diff;
			//Vector3 projVel = normalStore * this->mVelocity.GetDotProduct(normalStore);
			Vector3 newPo = origin + normalStore*diff;
			/*
			if( projVel.GetDotProduct(normalStore) < 0.0f)
			{
				newPo = origin - normalStore*diff;
				return false;
			}
			else
				newPo = origin + normalStore*diff;
			*/
			
			//this->SetPosition(newPo);
			b->SetTempPosition(newPo);
			normalPlane = normalStore;
			//this->mNormalContact = normalPlane;
			//this->mHasContact  = true;
			return true;
		}
		else
		{
			normalPlane = Vector3(0,0,0);
			//this->mNormalContact = normalPlane;
			//this->mHasContact  = false;
			return false;
		}
		
	}
	normalPlane = Vector3(0,0,0);
	b->SetNormalContact(normalPlane);
	//this->mHasContact  = false;
	return false;
}
Exemplo n.º 16
0
void Helicopter::Update(float dt)
{
	// Gravity
	this->direction.y -= GRAVITY * dt;

	// Air friction
	float velocity = this->GetVelocity();
	float newVelocity = velocity - ((AIR_FRICTION_CONSTANT * (velocity * velocity)) / this->mass) * dt;
	float dv = newVelocity / velocity;
	this->direction *= dv;
	
	
	// Collision against terrain
	float terrY = this->terrain->GetYPositionAt(this->pos.x, this->pos.z);
	if(this->pos.y + this->direction.y * dt <= terrY)
	{
		// Bounce
		this->direction.y = 0 - this->direction.y * this->elacticity;

		// Take damage
		float damage = (abs(this->direction.y * 5) + abs(this->direction.x) + abs(this->direction.z)); 
		if(damage > 5.0f)
			this->health -= damage;
	}


	// Regen health:
	this->health += dt;
	if(this->health > 100.0f)
		this->health = 100.0f;
	
	
	// Friction against terrain here if close to it, simplified calculating only in the XZ plane and not angled terrain.
	if(this->pos.y - 0.5f < terrY)
	{
		float frictionForce = GROUND_FRICTION_CONSTANT * this->mass * GRAVITY;
		float frictionAcc = (frictionForce / this->mass) * dt;
		if(frictionAcc > this->GetXZVelocity())
		{
			this->direction.x = 0;
			this->direction.z = 0;
		}
		else
		{
			velocity = this->GetVelocity();
			newVelocity = velocity - frictionAcc;
			dv = newVelocity / velocity;
			this->direction *= dv;
		}

		// Reset rolling when touching ground.
		Vector3 defup = Vector3(0, 1, 0);
		defup.Normalize();
		Vector3 cross = this->up.GetCrossProduct(this->forward);
		cross.Normalize();
		float dotCrossDefup = cross.GetDotProduct(defup);
		// Roll left
		if(dotCrossDefup < 0.0f)
		{
			this->RollLeft(true);
			this->RollRight(false);
		}
		// Roll right
		else if(dotCrossDefup > 0.0f)
		{
			this->RollLeft(false);
			this->RollRight(true);
		}

		float dotForUp = this->forward.GetDotProduct(defup);
		// Roll forward
		if(dotForUp > 0.0f)
		{
			this->RollForward(true);
			this->RollBackward(false);
		}
		// Roll backward
		else if(dotForUp < 0.0f)
		{
			this->RollForward(false);
			this->RollBackward(true);
		}
	}
	
	if(this->health > 95.0f)
		this->UpdateChopperSpec(dt);


	// For funness we need to reset the direction.y a little, it's too hard to handle up&downs otherwise
	//direction.y *= 1.0f - dt;

	// AutoHoverEffect
	this->AutoHover(dt);

	if(this->health > 95.0f)
	{
		this->pos += this->direction * dt;
		this->chopper->SetPosition(this->pos);
		this->rotor->SetPosition(this->pos);
		this->secrotor->SetPosition(this->pos - this->forward * 28 + this->up * 11);	// Adding offset for the second rotor.

		Vector3 lookAt = this->forward;
		lookAt.y = 0.0f;
		GetGraphics()->GetCamera()->SetPosition(this->pos + Vector3(0, this->camOffsetHeight, 0) - lookAt * this->camOffsetDistance);
		GetGraphics()->GetCamera()->LookAt(this->pos + lookAt * 30 + Vector3(0, 10, 0));


		// Attune forward to direction.
		Vector3 xzdir = this->direction;
		xzdir.y = 0.0f;
		float xzlen = xzdir.GetLength();
		xzdir.Normalize();
		Vector3 xzfor = this->forward;
		xzfor.y = 0.0f;
		xzfor.Normalize();
		float dotDirFor = xzdir.GetDotProduct(xzfor);
		Vector3 vecRight = xzfor.GetCrossProduct(Vector3(0, 1, 0));
		vecRight.y = 0.0f;
		vecRight.Normalize();
		float dotDirRight = xzdir.GetDotProduct(vecRight);

		// When flying backwards remove the "BAM SNAP" effect when dot product gets 0.0f at the sides.
		if(dotDirFor < 0.0f)
			dotDirFor = 0.0f;

		float angle = dt * xzlen * xzlen * xzlen * xzlen * (1 - abs(dotDirFor)) * 0.000001f;
		if(dotDirRight < 0.0f)
			angle *= -1.0f;
		this->forward.RotateAroundAxis(this->up, -angle);
		this->chopper->RotateAxis(this->up, -angle);
		this->rotor->RotateAxis(this->up, angle);
	}
}
Exemplo n.º 17
0
bool Plane<T>::IntersectsWithPlane( const Plane<T> &other ) const
{
   Vector3<T> cross = other.normal.CrossProduct(normal);
   return cross.GetLength() > ROUNDING_ERROR_FLT;
}