
AddCSLuaFile( "cl_init.lua" )
AddCSLuaFile( "shared.lua" )


/*---------------------------------------------------------
   Name: Initialize
---------------------------------------------------------*/
function ENT:Initialize()

	self.Entity:PhysicsInit( SOLID_VPHYSICS )
	self.Entity:SetMoveType( MOVETYPE_VPHYSICS )
	self.Entity:SetSolid( SOLID_VPHYSICS )
	
	local phys = self.Entity:GetPhysicsObject()
	
	if (phys:IsValid()) then
		phys:Wake()
	end
	
	local max = self.Entity:OBBMaxs()
	local min = self.Entity:OBBMins()
	
	self.ThrustOffset 	= Vector( 0, 0, max.z )
	self.ThrustOffsetR 	= Vector( 0, 0, min.z )
	self.ForceAngle		= self.ThrustOffset:GetNormalized() * -1
	
	self:SetForce( 2000 )
	
	self:SetEffect( self.EFFECT_FIRE )

	self.Entity:SetNetworkedVector( 0, self.ThrustOffset )
	self.Entity:StartMotionController()
	
	self:Switch( false )
	self.ActivateOnDamage = true
	
end


/*---------------------------------------------------------
   Name: SetEffect
---------------------------------------------------------*/
function ENT:SetEffect( type )

	self.Effect = type
	self.Entity:SetNetworkedInt( 1, self.Effect )
	
end


/*---------------------------------------------------------
   Name: SetForce
---------------------------------------------------------*/
function ENT:SetForce( force, mul )

	if (force) then	self.force = force end
	mul = mul or 1
	
	local phys = self.Entity:GetPhysicsObject()
	if (!phys:IsValid()) then 
		Msg("Warning: [gmod_thruster] Physics object isn't valid!\n")
		return 
	end
	
	// Get the data in worldspace
	local ThrusterWorldPos = phys:LocalToWorld( self.ThrustOffset )
	local ThrusterWorldForce = phys:LocalToWorldVector( self.ThrustOffset * -1 )
	
	// Calculate the velocity
	ThrusterWorldForce = ThrusterWorldForce * self.force * mul
	self.ForceLinear, self.ForceAngle = phys:CalculateVelocityOffset( ThrusterWorldForce, ThrusterWorldPos );
	self.ForceLinear = phys:WorldToLocalVector( self.ForceLinear )
	
	if ( mul > 0 ) then
		self.Entity:SetNetworkedVector( 0, self.ThrustOffset )
	else
		self.Entity:SetNetworkedVector( 0, self.ThrustOffsetR )
	end
	
	self.Entity:SetNetworkedVector( 1, self.ForceAngle )
	self.Entity:SetNetworkedVector( 2, self.ForceLinear )
	
end


/*---------------------------------------------------------
   Called when keypad key is pressed
---------------------------------------------------------*/
function ENT:InputActivate( mul )

	if ( self:GetToggle() ) then 
	
		return self:Switch( !self:IsOn(), mul )
	
	end

	return self:Switch( true, mul )
	
end

/*---------------------------------------------------------
   Called when keypad key is released
---------------------------------------------------------*/
function ENT:InputDeactivate( mul )

	if ( self:GetToggle() ) then return true end
	
	return self:Switch( false, mul )
	
end

/*---------------------------------------------------------
   Name: OnTakeDamage
---------------------------------------------------------*/
function ENT:OnTakeDamage( dmginfo )

	self.Entity:TakePhysicsDamage( dmginfo )

	if !self.ActivateOnDamage then return end

	self:Switch( true, 1 )
	timer.Create( self, 5, 1, function(...) self:Switch(...) end, false, 1 )

end


/*---------------------------------------------------------
   Name: Use
---------------------------------------------------------*/
function ENT:Use( activator, caller )
end

/*---------------------------------------------------------
   Name: Simulate
---------------------------------------------------------*/
function ENT:PhysicsSimulate( phys, deltatime )

	if (!self.On) then return SIM_NOTHING end
	
	local ForceAngle, ForceLinear = self.ForceAngle, self.ForceLinear

	return ForceAngle, ForceLinear, SIM_LOCAL_ACCELERATION
	
end

/*---------------------------------------------------------
   Switch thruster on or off
---------------------------------------------------------*/
function ENT:Switch( on, mul )
	
	if (!self.Entity:IsValid()) then return false end
	
	self.On = on
	
	if (on) then 
		self.Entity:SetNetworkedInt( 0, mul ) 
		self:SetForce( nil, mul )
	else 
		self.Entity:SetNetworkedInt( 0, 0 ) end
	
	local phys = self.Entity:GetPhysicsObject()
	if (phys:IsValid()) then
		phys:Wake()
	end
	
	return true
	
end

/*---------------------------------------------------------
   Returns true if thruster is on
---------------------------------------------------------*/
function ENT:IsOn()
	return self.On
end

/*---------------------------------------------------------
   Sets whether this is a toggle thruster or not
---------------------------------------------------------*/
function ENT:SetToggle(tog)
	self.Toggle = tog
end

/*---------------------------------------------------------
   Returns true if this is a toggle thruster
---------------------------------------------------------*/
function ENT:GetToggle()
	return self.Toggle
end


/*---------------------------------------------------------
   Numpad control functions
   These are layed out like this so it'll all get saved properly
---------------------------------------------------------*/
local function On( pl, ent, mul )
	if (!ent:IsValid()) then return false end
	return ent:GetTable():InputActivate( mul )
end

local function Off( pl, ent, mul )
	if (!ent:IsValid()) then return false end
	return ent:GetTable():InputDeactivate( mul )
end

// register numpad functions
numpad.Register( "Thruster_On", On )
numpad.Register( "Thruster_Off", Off )

include('shared.lua')
