-- -- Spirit600SXL -- Specialization for Spirit600SXL -- -- @author (Flagsystems) Manuel Leithner -- @version v1.0 -- @date 13/05/11 -- @history: v1.0 - Initial version -- Spirit600SXL = {}; function Spirit600SXL.prerequisitesPresent(specializations) return true; end; function Spirit600SXL:load(xmlFile) self.setLowerDiscs = SpecializationUtil.callSpecializationsFunction("setLowerDiscs"); self.setLowerMarker = SpecializationUtil.callSpecializationsFunction("setLowerMarker"); self.getIsAreaActive = Utils.overwrittenFunction(self.getIsAreaActive, Spirit600SXL.getIsAreaActive); self.isNextMarkerLeft = true; self.marker = {}; self.marker.left = {}; self.marker.left.isDown = false; self.marker.left.index = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.markers.left#index")); self.marker.left.area = self.cuttingAreas[getXMLInt(xmlFile, "vehicle.markers.left#area")]; self.marker.left.activation = Utils.degToRad(getXMLFloat(xmlFile, "vehicle.markers.left#activation")); self.marker.right = {}; self.marker.right.isDown = false; self.marker.right.index = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.markers.right#index")); self.marker.right.area = self.cuttingAreas[getXMLInt(xmlFile, "vehicle.markers.right#area")]; self.marker.right.activation = Utils.degToRad(getXMLFloat(xmlFile, "vehicle.markers.right#activation")); self.marker.back = {}; self.marker.back.isDown = false; self.marker.back.index = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.markers.back#index")); self.marker.back.area1 = self.cuttingAreas[getXMLInt(xmlFile, "vehicle.markers.back#area1")]; self.marker.back.area2 = self.cuttingAreas[getXMLInt(xmlFile, "vehicle.markers.back#area2")]; self.marker.back.activation = Utils.degToRad(getXMLFloat(xmlFile, "vehicle.markers.back#activation")); self.thresholds = {}; self.thresholds.discIndex = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.thresholds#discIndex")); self.thresholds.discActivation = Utils.degToRad(getXMLFloat(xmlFile, "vehicle.thresholds#discActivation")); self.thresholds.seedingIndex = Utils.indexToObject(self.components, getXMLString(xmlFile, "vehicle.thresholds#seedingIndex")); self.thresholds.seedingActivation = Utils.degToRad(getXMLFloat(xmlFile, "vehicle.thresholds#seedingActivation")); self.aiTerrainDetailChannel1 = g_currentMission.cultivatorChannel; self.aiTerrainDetailChannel2 = g_currentMission.ploughChannel; ---1; activate when ai doesn't work anymore self.groundReferenceNodeBackup = self.groundReferenceNode; self.activeAIHelperTime = 0; self.foldWarningTime = 0; self.activateMarkerTime = 0; self.frontMarkerDistanceScaleBackup = nil; self.attacherVehicleBackup = nil; self.areDiscsLowered = false; self.doAIActivationCheck = false; self.contactReportNodes = {}; end; function Spirit600SXL:delete() Utils.deleteParticleSystem(self.groundParticleSystems); for _, entry in ipairs(self.newGroundParticleSystems) do Utils.deleteParticleSystem(entry.ps); end; self.groundParticleSystems = {}; self.newGroundParticleSystems = {}; end; function Spirit600SXL:readStream(streamId, connection) self:setLowerDiscs(streamReadBool(streamId), true); self:setLowerMarker(1, streamReadBool(streamId), true); self:setLowerMarker(2, streamReadBool(streamId), true); self:setLowerMarker(3, streamReadBool(streamId), true); end; function Spirit600SXL:writeStream(streamId, connection) streamWriteBool(streamId, self.areDiscsLowered); streamWriteBool(streamId, self.marker.left.isDown); streamWriteBool(streamId, self.marker.right.isDown); streamWriteBool(streamId, self.marker.back.isDown); end; function Spirit600SXL:mouseEvent(posX, posY, isDown, isUp, button) end; function Spirit600SXL:keyEvent(unicode, sym, modifier, isDown) end; function Spirit600SXL:update(dt) if self:getIsActiveForInput() then if InputBinding.hasEvent(InputBinding.LOWER_IMPLEMENT) or InputBinding.hasEvent(InputBinding.FASTSEEDER_LOWER_LEFTMARKER) or InputBinding.hasEvent(InputBinding.FASTSEEDER_LOWER_RIGHTMARKER) or InputBinding.hasEvent(InputBinding.FASTSEEDER_LOWER_BACKMARKER) then if self.foldAnimTime == nil or (self.foldAnimTime <= 1.0 and self.foldAnimTime >= 0.8) then if not self.isAIActive then if InputBinding.hasEvent(InputBinding.LOWER_IMPLEMENT) then self:setLowerDiscs(not self.areDiscsLowered); end; if InputBinding.hasEvent(InputBinding.FASTSEEDER_LOWER_LEFTMARKER) then self:setLowerMarker(1, not self.marker.left.isDown); end; if InputBinding.hasEvent(InputBinding.FASTSEEDER_LOWER_RIGHTMARKER) then self:setLowerMarker(2, not self.marker.right.isDown); end; if InputBinding.hasEvent(InputBinding.FASTSEEDER_LOWER_BACKMARKER) then self:setLowerMarker(3, not self.marker.back.isDown); end; else self.activeAIHelperTime = self.time + 2000; end; else self.foldWarningTime = self.time + 2000; end; end; end; end; function Spirit600SXL:updateTick(dt) if self:getIsActive() then local x,_,_ = getRotation(self.thresholds.discIndex); if x > self.thresholds.discActivation then self.groundReferenceNode = self.groundReferenceNodeBackup; self.checkSpeedLimit = true; else self.groundReferenceNode = nil; self.checkSpeedLimit = false; end; if self.doAIActivationCheck then _,ly,_ = getRotation(self.marker.left.index); _,ry,_ = getRotation(self.marker.right.index); local leftActive = ly < self.marker.left.activation; local rightActive = ry > self.marker.right.activation; if not ((leftActive and not rightActive) or (not leftActive and rightActive)) then if self.attacherVehicle ~= nil then self.attacherVehicle:stopAITractor(); self.activateMarkerTime = self.time + 2000; end; else self:setLowerMarker(3, false, true); self:setLowerDiscs(true, true); end; self.doAIActivationCheck = false; end; for _, part in pairs(self.movingParts) do Cylindered.updateMovingPart(self, part); end; end; end; function Spirit600SXL:setFoldDirection(direction, noEventSend) if direction == -1 then local animTime = nil; if self:getIsAnimationPlaying("middleFold") then animTime = self:getAnimationTime("middleFold"); end; self:playAnimation("middleFold", -1, animTime, true); self:setLowerMarker(1, false, true); self:setLowerMarker(2, false, true); self:setLowerMarker(3, false, true); end; end; function Spirit600SXL:draw() if self.areDiscsLowered then g_currentMission:addHelpButtonText(string.format(g_i18n:getText("DISCS_LIFT"), self.typeDesc), InputBinding.LOWER_IMPLEMENT); else g_currentMission:addHelpButtonText(string.format(g_i18n:getText("DISCS_LOWER"), self.typeDesc), InputBinding.LOWER_IMPLEMENT); end; local leftMarkerKey = InputBinding.getKeyNamesOfDigitalAction(InputBinding.FASTSEEDER_LOWER_LEFTMARKER); local rightMarkerKey = InputBinding.getKeyNamesOfDigitalAction(InputBinding.FASTSEEDER_LOWER_RIGHTMARKER); local backMarkerKey = InputBinding.getKeyNamesOfDigitalAction(InputBinding.FASTSEEDER_LOWER_BACKMARKER); g_currentMission:addExtraPrintText(string.format(g_i18n:getText("CONTROL_MARKERS"), leftMarkerKey .. "/" .. rightMarkerKey .. "/" .. backMarkerKey)); if self.activeAIHelperTime > self.time then g_currentMission:addWarning(g_i18n:getText("AI_TRACTOR_WARNING"), 0.018, 0.033); end; local foldingKey = InputBinding.getKeyNamesOfDigitalAction(InputBinding.IMPLEMENT_EXTRA2); if self.foldWarningTime > self.time then g_currentMission:addWarning(string.format(g_i18n:getText("UNFOLD_FIRST"), foldingKey), 0.018, 0.033); end; if self.activateMarkerTime > self.time then g_currentMission:addWarning(string.format(g_i18n:getText("UNFOLD_MARKER"), leftMarkerKey .. "/" .. rightMarkerKey), 0.018, 0.033); end; end; function Spirit600SXL:setLowerDiscs(areDown, noEventSend) SetLowerDiscsEvent.sendEvent(self, areDown, noEventSend); self.areDiscsLowered = areDown; local animTime = nil; local animation = "workingFold"; if areDown then animation = "workingUnfold"; end; if self:getIsAnimationPlaying(animation) then animTime = self:getAnimationTime(animation); end; self:playAnimation(animation, 1, animTime, true); self.doCheckForActivation = true; end; function Spirit600SXL:setLowerMarker(markerId, isDown, noEventSend) SetLowerMarkerEvent.sendEvent(self, markerId, isDown, noEventSend); local animTime = nil; local direction = 1; if not isDown then direction = -1; end; local animation = nil; if markerId == 1 then animation = "leftMarkerFold"; self.marker.left.isDown = isDown; elseif markerId == 2 then animation = "rightMarkerFold"; self.marker.right.isDown = isDown; elseif markerId == 3 then animation = "backMarkerFold"; self.marker.back.isDown = isDown; end; if self:getIsAnimationPlaying(animation) then animTime = self:getAnimationTime(animation); end; self:playAnimation(animation, direction, animTime, true); end; function Spirit600SXL:getIsAreaActive(superFunc, area) local isActive = false; if area == self.marker.left.area then _,y,_ = getRotation(self.marker.left.index); isActive = y < self.marker.left.activation; elseif area == self.marker.right.area then _,y,_ = getRotation(self.marker.right.index); isActive = y > self.marker.right.activation; elseif area == self.marker.back.area1 or area == self.marker.back.area2 then x,_,_ = getRotation(self.marker.back.index); isActive = x < self.marker.back.activation; else if area.cultivator then local x,_,_ = getRotation(self.thresholds.discIndex); isActive = x > self.thresholds.discActivation; else local x,_,_ = getRotation(self.thresholds.seedingIndex); isActive = x < self.thresholds.seedingActivation; end; end; if superFunc ~= nil then return superFunc(self, area) and isActive; end; return isActive; end; function Spirit600SXL:aiTurnOff() if not self.doAIActivationCheck then self:setLowerMarker(1, false, true); self:setLowerMarker(2, false, true); self:setLowerMarker(3, false, true); self:setLowerDiscs(false, true); end; self.isAIActive = false; end; function Spirit600SXL:aiTurnOn() self.isAIActive = true; self.doAIActivationCheck = true; end; function Spirit600SXL:aiLower() if self.isServer then if self.isNextMarkerLeft then self:setLowerMarker(1, true); else self:setLowerMarker(2, true); end; self:setLowerDiscs(true); end; end; function Spirit600SXL:aiRaise() self:setLowerMarker(1, false, true); self:setLowerMarker(2, false, true); self:setLowerDiscs(false, true); end; function Spirit600SXL:aiInvertsMarkerOnTurn(turnLeft) self.isNextMarkerLeft = not turnLeft; return false; end; function Spirit600SXL:onAttach(attacherVehicle) Cultivator.removeContactReports(self); self.attacherVehicleBackup = attacherVehicle; if attacherVehicle.frontMarkerDistanceScale then self.frontMarkerDistanceScaleBackup = attacherVehicle.frontMarkerDistanceScale; attacherVehicle.frontMarkerDistanceScale = 0.5; end; end; function Spirit600SXL:onDetach() if self.frontMarkerDistanceScaleBackup ~= nil then self.attacherVehicleBackup.frontMarkerDistanceScale = self.frontMarkerDistanceScaleBackup; self.frontMarkerDistanceScaleBackup = nil; end; self.attacherVehicleBackup = nil; end;