--
-- JCB_8310
-- Specialization class for JCB 8310
--
-- @author  PeterJ - euroDZN
-- @date  16/11/2012
--
-- http://eurodzn.wordpress.com/
--
-- Copyright (C) euroDZN, Confidential, All Rights Reserved.

JCB_8310 = {};

function JCB_8310.prerequisitesPresent(specializations)
    return SpecializationUtil.hasSpecialization(Steerable, specializations);
end;

function JCB_8310:load(xmlFile)
	
	local clutchPart = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.clutch#index"));
    if clutchPart ~= nil then
        self.clutch = {};
        self.clutch.node = clutchPart;

        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.clutch#minRot"));
        self.clutch.minRot = {};
        self.clutch.minRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.clutch.minRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.clutch.minRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));

        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.clutch#maxRot"));
        self.clutch.maxRot = {};
        self.clutch.maxRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.clutch.maxRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.clutch.maxRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));

        self.clutch.rotTime = Utils.getNoNil(getXMLString(xmlFile, "vehicle.clutch#rotTime"), 2)*1000;
    end;
	local brakesPart = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.brakes#index"));
    if brakesPart ~= nil then
        self.brakes = {};
        self.brakes.node = brakesPart;

        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.brakes#minRot"));
        self.brakes.minRot = {};
        self.brakes.minRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.brakes.minRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.brakes.minRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));

        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.brakes#maxRot"));
        self.brakes.maxRot = {};
        self.brakes.maxRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.brakes.maxRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.brakes.maxRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));

        self.brakes.rotTime = Utils.getNoNil(getXMLString(xmlFile, "vehicle.brakes#rotTime"), 2)*1000;
    end;
	local throttlePart = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.throttle#index"));
    if throttlePart ~= nil then
        self.throttle = {};
        self.throttle.node = throttlePart;

        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.throttle#minRot"));
        self.throttle.minRot = {};
        self.throttle.minRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.throttle.minRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.throttle.minRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));

        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.throttle#maxRot"));
        self.throttle.maxRot = {};
        self.throttle.maxRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.throttle.maxRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.throttle.maxRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));
	end;
	local joystickPart = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.joystick#index"));
	if joystickPart ~= nil then
		self.joystick = {};
        self.joystick.node = joystickPart;

        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.joystick#minRot"));
        self.joystick.minRot = {};
        self.joystick.minRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.joystick.minRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.joystick.minRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));

        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.joystick#maxRot"));
        self.joystick.maxRot = {};
        self.joystick.maxRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.joystick.maxRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.joystick.maxRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));
		
        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.joystick#neutral"));
        self.joystick.neutral = {};
        self.joystick.neutral[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.joystick.neutral[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.joystick.neutral[3] = Utils.degToRad(Utils.getNoNil(z, 0));

        self.joystick.rotTime = Utils.getNoNil(getXMLString(xmlFile, "vehicle.joystick#rotTime"), 2)*1000;
	end;
	local rotationPartFuel = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.needles.fuel#index"));
    if rotationPartFuel ~= nil then
        self.rotationFuel = {};
        self.rotationFuel.node = rotationPartFuel;

        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.needles.fuel#minRot"));
        self.rotationFuel.minRot = {};
        self.rotationFuel.minRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.rotationFuel.minRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.rotationFuel.minRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));

        x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.needles.fuel#maxRot"));
        self.rotationFuel.maxRot = {};
        self.rotationFuel.maxRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.rotationFuel.maxRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.rotationFuel.maxRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));
		
		self.fuelLight = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.needles.fuel#lightIndicator"));
	end;
	local rotationPartTemp = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.needles.temperature#index"));
    if rotationPartTemp ~= nil then
        self.rotationTemp = {};
        self.rotationTemp.node = rotationPartTemp;

        local x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.needles.temperature#minRot"));
        self.rotationTemp.minRot = {};
        self.rotationTemp.minRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.rotationTemp.minRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.rotationTemp.minRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));

        x, y, z = Utils.getVectorFromString(getXMLString(xmlFile, "vehicle.needles.temperature#maxRot"));
        self.rotationTemp.maxRot = {};
        self.rotationTemp.maxRot[1] = Utils.degToRad(Utils.getNoNil(x, 0));
        self.rotationTemp.maxRot[2] = Utils.degToRad(Utils.getNoNil(y, 0));
        self.rotationTemp.maxRot[3] = Utils.degToRad(Utils.getNoNil(z, 0));

        self.rotationTemp.rotTime = Utils.getNoNil(getXMLString(xmlFile, "vehicle.needles.temperature#rotTime"), 2)*1000;
    end;
	if rotationPartFuel ~= nil or rotationPartTemp ~= nil then 
		self.hasNeedles = true;
	end;
	self.toplink = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.attachers#topLink"));
	self.toplink2 = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.attachers#topLink2"));
 	setVisibility(self.toplink, false);
 	setVisibility(self.toplink2, true);
	self.highHitch = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.attachers#highHitch"));
	
	self.backArmsAnim = getXMLString(xmlFile, "vehicle.backArmsAnim#animationName");
	self.frontArmsAnim = getXMLString(xmlFile, "vehicle.frontArmsAnim#animationName");
	self.frontArmsAnim2 = getXMLString(xmlFile, "vehicle.frontArmsAnim#animationName2");
	self.joystickAnim = getXMLString(xmlFile, "vehicle.joystickAnim#animationName");
	self.joystickAnim2 = getXMLString(xmlFile, "vehicle.joystickAnim#animationName2");
	
	self.leftFender = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.fenders#left"));
	self.rightFender = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.fenders#right"));
	
	self.dashLightOn = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.dashLights#index"));
	
	self.touchScreen1 = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.touchScreen#speedUnit"));
	self.touchScreen2 = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.touchScreen#speedLevel"));
	self.touchScreenBar = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.touchScreen#percentageBar"));
	
	self.seatNode = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.seatAnim#node"));
	self.seatOffset = Utils.getNoNil(getXMLFloat(xmlFile, "vehicle.seatAnim#seatOffset"), 0.03);
	if self.seatNode ~=nil then
		local x,y,z = getTranslation(self.seatNode);
		self.seatXTrans = x;
		self.seatYTrans = y;
		self.seatZTrans = z;
		local _,y,_ = getTranslation(self.wheels[1].repr);
		local _,y1,_ = getTranslation(self.wheels[3].repr);
		self.axlesYdiff = y1-y;
	end;
	
	self.deactivateHose = Utils.getNoNil(getXMLBool(xmlFile, "vehicle.hydraulicHose#deactivate"), false);	
	if not self.deactivateHose then	
		local i=0;
		while true do
			local baseName = string.format("vehicle.attacherJoints.attacherJoint(%d)", i);
			local index = getXMLString(xmlFile, baseName.. "#index");
			if index == nil then
				break;
			end;		
			local joint = self.attacherJoints[i+1];
			local hoseAttacher = Utils.indexToObject(self.components, getXMLString(xmlFile, baseName .. "#hose"));
			if hoseAttacher ~= nil then
				joint.hydrahoseAttacher = hoseAttacher;
			end;
			i = i + 1;
		end;

		local attacherJointCount = i;
		i = 0;
		while true do
			local baseName = string.format("vehicle.trailerAttacherJoints.trailerAttacherJoint(%d)", i);
			local index = getXMLString(xmlFile, baseName.. "#index");
			if index == nil then
				break;
			end;
			
			local joint = self.attacherJoints[attacherJointCount + 1 + i];
			local hoseAttacher = Utils.indexToObject(self.components, getXMLString(xmlFile, baseName .. "#hose"));
			if hoseAttacher ~= nil then
				joint.hydrahoseAttacher = hoseAttacher;
			end;
			i = i+1;
		end;
	end;
	
end;

function JCB_8310:delete()
end;

function JCB_8310:mouseEvent(posX, posY, isDown, isUp, button)
end;

function JCB_8310:keyEvent(unicode, sym, modifier, isDown)
end;

function JCB_8310:update(dt)
	if self:getIsActive() then
		if self:getIsActiveForInput(false) then
			if InputBinding.hasEvent(InputBinding.SPEED_LEVEL1) or InputBinding.hasEvent(InputBinding.SPEED_LEVEL2) or InputBinding.hasEvent(InputBinding.SPEED_LEVEL3) or InputBinding.hasEvent(InputBinding.SPEED_LEVEL4) then
				if self.joystickAnim ~= nil and self.playAnimation ~= nil then
					self:playAnimation(self.joystickAnim, 1, nil, true);
				end;
			end;
		end;
		if self.clutch ~= nil then
			local x, y, z = getRotation(self.clutch.node);
			local rot = {x,y,z};
			local newRot = Utils.getMovedLimitedValues(rot, self.clutch.maxRot, self.clutch.minRot, 3, self.clutch.rotTime, dt, (self.brakeLightsVisibility or self.movingDirection == 0));
			setRotation(self.clutch.node, unpack(newRot));
		end;
		if self.brakes ~= nil then
			local x, y, z = getRotation(self.brakes.node);
			local rot = {x,y,z};
			local newRot = Utils.getMovedLimitedValues(rot, self.brakes.maxRot, self.brakes.minRot, 3, self.brakes.rotTime, dt, (self.brakeLightsVisibility or self.movingDirection == 0));
			setRotation(self.brakes.node, unpack(newRot));
		end;
		local maxThrottle = 1500;
		if self.throttle ~= nil and self.isMotorStarted then
			local x, y, z = getRotation(self.throttle.node);
			x = ((self.throttle.maxRot[1] - self.throttle.minRot[1]) / maxThrottle) * (self.motor.lastMotorRpm/1.5) + self.throttle.minRot[1];
			y = ((self.throttle.maxRot[2] - self.throttle.minRot[2]) / maxThrottle) * (self.motor.lastMotorRpm/1.5) + self.throttle.minRot[2];
			z = ((self.throttle.maxRot[3] - self.throttle.minRot[3]) / maxThrottle) * (self.motor.lastMotorRpm/1.5) + self.throttle.minRot[3];
			setRotation(self.throttle.node, x, y ,z);
		elseif not self.isMotorStarted then
			setRotation(self.throttle.node, self.throttle.minRot[1], self.throttle.minRot[2], self.throttle.minRot[3]);
		end;
		if self.joystick.node ~= nil then
			if self.ESLimiter.isButtonPressed and self.ESLplus ~= nil then
				local x, y, z = getRotation(self.joystick.node);
				local rot = {x,y,z};
				local newRot = Utils.getMovedLimitedValues(rot, self.joystick.maxRot, self.joystick.minRot, 3, self.joystick.rotTime, dt, self.ESLplus);
				setRotation(self.joystick.node, unpack(newRot));
				self.joystickUp = self.ESLplus;
			else
				local x, y, z = getRotation(self.joystick.node);
				local rot = {x,y,z};
				if self.joystickUp then 
					local newRot = Utils.getMovedLimitedValues(rot, self.joystick.maxRot, self.joystick.neutral, 3, self.joystick.rotTime/2, dt, true);
					setRotation(self.joystick.node, unpack(newRot));
				else
					local newRot = Utils.getMovedLimitedValues(rot, self.joystick.minRot, self.joystick.neutral, 3, self.joystick.rotTime/2, dt, true);
					setRotation(self.joystick.node, unpack(newRot));
				end;
			end;
		end;
		if self.hasNeedles then
			if self.isMotorStarted then
				if self.rotationFuel.node ~= nil then
					local x, y, z = getRotation(self.rotationFuel.node);
					x = (self.rotationFuel.maxRot[1] - self.rotationFuel.minRot[1]) * (self.fuelFillLevel/self.fuelCapacity);
					y = (self.rotationFuel.maxRot[2] - self.rotationFuel.minRot[2]) * (self.fuelFillLevel/self.fuelCapacity);
					z = (self.rotationFuel.maxRot[3] - self.rotationFuel.minRot[3]) * (self.fuelFillLevel/self.fuelCapacity);
					setRotation(self.rotationFuel.node, x, y, z);
				end;
				self.operateNeedles = true;
				if self.fuelLight ~= nil then
					local fuelWarnPercentage = 20;
					local currentFuelPercentage = (self.fuelFillLevel / self.fuelCapacity + 0.0001) * 100;
					setVisibility(self.fuelLight, currentFuelPercentage < fuelWarnPercentage);
				end;
			else
				setRotation(self.rotationFuel.node, self.rotationFuel.minRot[1], self.rotationFuel.minRot[2], self.rotationFuel.minRot[3]);
				self.operateNeedles = false;
				setVisibility(self.fuelLight, false);
			end;
			if self.rotationTemp.node ~= nil then
				local x, y, z = getRotation(self.rotationTemp.node);
				local rot = {x,y,z};
				local newRot = Utils.getMovedLimitedValues(rot, self.rotationTemp.maxRot, self.rotationTemp.minRot, 3, self.rotationTemp.rotTime, dt, not self.operateNeedles);
				setRotation(self.rotationTemp.node, unpack(newRot));
			end;
		end;
		if self.joystickAnim ~= nil and self.joystickAnim2 ~= nil then
			if self.movingDirection ~= 0 and self.lastMovedDistance > 0.015 then
				if self.movingDirection > 0 then
					if self.moveLever then
						self:playAnimation(self.joystickAnim, 1, nil, true);
						self.moveLever = false;
					end;
				else
					if not self.moveLever then
						self:playAnimation(self.joystickAnim2, 1, nil, true);
						self.moveLever = true;
					end;
				end;
			end;
		end;
	end;
	if self.leftFender ~= nil then
		local _,leftWheelRot,_ = getRotation(self.wheels[2].repr);
		if leftWheelRot > 0 then
			setRotation(self.leftFender, 0, -leftWheelRot, 0);
		end;
	end;
	if self.rightFender ~= nil then
		local _,rightWheelRot,_ = getRotation(self.wheels[1].repr);
		if rightWheelRot < 0 then
			setRotation(self.rightFender, 0, -rightWheelRot, 0);
		end;
	end;
	if self.dashLightOn ~= nil then
		setVisibility(self.dashLightOn, self.isMotorStarted);
	end;
end;

function JCB_8310:updateTick(dt)
	
	if self:getIsActive() then
		if self.seatNode ~= nil then
			local _,y,_ = getTranslation(self.wheels[1].repr);
			local _,y2,_ = getTranslation(self.wheels[2].repr);
			local _,y3,_ = getTranslation(self.wheels[3].repr);
			local _,y4,_ = getTranslation(self.wheels[4].repr);
			local YtransFt = 0;
			local YtransBk = 0;
			if y > y2 then
				YtransFt = (y - y2);
			else
				YtransFt = (y2 - y);
			end;
			if y3 > y4 then
				YtransBk = (y3 - y4);
			else
				YtransBk = (y4 - y3);
			end;
			local axlesYtrans = 0;
			if self.axlesYdiff ~= (y3 - y) then
				axlesYtrans = self.axlesYdiff - (y3 - y);
			end;
			local Ytrans = (YtransFt + YtransBk + axlesYtrans)/3;
			if Ytrans > self.seatOffset then
				Ytrans = self.seatOffset;
			elseif Ytrans < -self.seatOffset then
				Ytrans = -self.seatOffset;
			end;
			setTranslation(self.seatNode, self.seatXTrans, self.seatYTrans-Ytrans, self.seatZTrans);
		end;
		if self.touchScreen1 ~= nil then
			setVisibility(self.touchScreen1, self.isMouseActive);
		end;
		if self.touchScreen2 ~= nil then
			setVisibility(self.touchScreen2, self.renderTouchScreen);
			if self.touchScreenBar ~= nil then
				setScale(self.touchScreenBar, self.barScale, 1, 1);
			end;
		end;
	end;
end;

function JCB_8310:draw()
end;

function JCB_8310:attachImplement(implement)
	local jointType = implement.object.attacherJoint.jointType;
	local jointIndex = implement.jointDescIndex;
	
	if jointType == Vehicle.JOINTTYPE_IMPLEMENT then
		if jointIndex == 1 then
			setVisibility(self.highHitch, false);
		elseif jointIndex == 2 then
			setVisibility(self.toplink, true);
			setVisibility(self.toplink2, false);
			if self.frontArmsAnim ~= nil and self.playAnimation ~= nil then
				self:playAnimation(self.frontArmsAnim, 15, nil, true);
			end;	
		end;
	elseif jointType == Vehicle.JOINTTYPE_TRAILER then
		if jointIndex == 3 then
			self.highTrailerAttached = true;
			if self.backArmsAnim ~= nil then
				self:playAnimation(self.backArmsAnim, 1, nil, true);
			end;
		elseif jointIndex == 5 then
			if self.frontArmsAnim ~= nil and self.frontArmsAnim2 ~= nil then
				self:playAnimation(self.frontArmsAnim, 2, nil, true);
				self:playAnimation(self.frontArmsAnim2, 1, nil, true);
			end;
		end;
	end;
end;

function JCB_8310:detachImplement(implementIndex)
	local implement = self.attachedImplements[implementIndex];
	local jointIndex = implement.jointDescIndex;
	local jointType = implement.object.attacherJoint.jointType;
	self.liftArmsLever = false;
		
	if jointIndex == 1 then
		setVisibility(self.highHitch, true);
	elseif jointIndex == 2 then
		setVisibility(self.toplink, false);
		setVisibility(self.toplink2, true);
		if self.frontArmsAnim ~= nil and self.playAnimation ~= nil then
			self:playAnimation(self.frontArmsAnim, -1, nil, true);
		end;
	elseif jointIndex == 3 then
			self.highTrailerAttached = false;
			if self.backArmsAnim ~= nil then
				self:playAnimation(self.backArmsAnim, -1, nil, true);
			end;
	elseif jointIndex == 5 then
		if self.frontArmsAnim ~= nil and self.frontArmsAnim2 ~= nil then
			self:playAnimation(self.frontArmsAnim, -1, nil, true);
			self:playAnimation(self.frontArmsAnim2, -1, nil, true);
		end;
	end;
end;
