LUADOC - Farming Simulator 19

Script v1.7.1.0

Engine v1.7.1.0

Foundation Reference

Windrower

Description
Specialization for windrowers providing additional animations, effects and drop area functionalities
Functions

doCheckSpeedLimit

Description
Definition
doCheckSpeedLimit()
Code
318function Windrower:doCheckSpeedLimit(superFunc)
319 local turnOn = true
320 if self.getIsTurnedOn ~= nil then
321 turnOn = self:getIsTurnedOn()
322 end
323
324 return superFunc(self) or (self:getIsImplementChainLowered() and turnOn)
325end

getDefaultSpeedLimit

Description
Definition
getDefaultSpeedLimit()
Code
394function Windrower.getDefaultSpeedLimit()
395 return 15
396end

getDirtMultiplier

Description
Definition
getDirtMultiplier()
Code
429function Windrower:getDirtMultiplier(superFunc)
430 local spec = self.spec_windrower
431
432 local multiplier = superFunc(self)
433
434 if spec.isWorking then
435 multiplier = multiplier + self:getWorkDirtMultiplier() * self:getLastSpeed() / self.speedLimit
436 end
437
438 return multiplier
439end

getWearMultiplier

Description
Definition
getWearMultiplier()
Code
443function Windrower:getWearMultiplier(superFunc)
444 local spec = self.spec_windrower
445
446 local multiplier = superFunc(self)
447
448 if spec.isWorking then
449 multiplier = multiplier + self:getWorkWearMultiplier() * self:getLastSpeed() / self.speedLimit
450 end
451
452 return multiplier
453end

initSpecialization

Description
Definition
initSpecialization()
Code
15function Windrower.initSpecialization()
16 g_workAreaTypeManager:addWorkAreaType("windrower", false)
17end

loadRakeFromXML

Description
Definition
loadRakeFromXML()
Code
329function Windrower:loadRakeFromXML(rake, xmlFile, key, index)
330 XMLUtil.checkDeprecatedXMLElements(self.xmlFile, self.configFileName, key.."#index", key.."#node") --FS17 to FS19
331
332 rake.node = I3DUtil.indexToObject(self.components, getXMLString(self.xmlFile, key.."#node"), self.i3dMappings)
333 rake.spikes = {}
334 rake.maxRotZ = math.rad(getXMLFloat(xmlFile, key.."#spikeMaxRotZ"))
335 rake.dir = Utils.getNoNil(getXMLInt(xmlFile, key.."#dir"), 1)
336
337 local moveUpRange = StringUtil.getRadiansFromString(getXMLString(xmlFile, key.."#moveUpRange"), 2)
338 local moveDownRange = StringUtil.getRadiansFromString(getXMLString(xmlFile, key.."#moveDownRange"), 2)
339 rake.moveUpStart = moveUpRange[1]
340 rake.moveUpEnd = moveUpRange[2]
341 rake.moveDownStart = moveDownRange[1]
342 rake.moveDownEnd = moveDownRange[2]
343
344 local j = 0
345 while true do
346 local spikeKey = string.format(key..".spike(%d)", j)
347 if not hasXMLProperty(xmlFile, spikeKey) then
348 break
349 end
350
351 XMLUtil.checkDeprecatedXMLElements(self.xmlFile, self.configFileName, spikeKey.."#index", spikeKey.."#node") --FS17 to FS19
352
353 local spike = {}
354 spike.node = I3DUtil.indexToObject(self.components, getXMLString(xmlFile, spikeKey.."#node"), self.i3dMappings)
355 spike.dir = Utils.getNoNil(getXMLInt(xmlFile, spikeKey.."#dir"), 1)
356 local _,y,_ = getRotation(getParent(spike.node))
357 spike.yRotOffset = y
358 table.insert(rake.spikes, spike)
359 j = j + 1
360 end
361
362 rake.yRotOffset = (2*math.pi) / #rake.spikes
363
364 return true
365end

loadWorkAreaFromXML

Description
Definition
loadWorkAreaFromXML()
Code
400function Windrower:loadWorkAreaFromXML(superFunc, workArea, xmlFile, key)
401 local retValue = superFunc(self, workArea, xmlFile, key)
402
403 if workArea.type == WorkAreaType.DEFAULT then
404 workArea.type = WorkAreaType.WINDROWER
405 end
406
407 if workArea.type == WorkAreaType.WINDROWER then
408 workArea.particleSystemIndex = getXMLInt(xmlFile, key .. ".windrower#particleSystemIndex")
409 workArea.dropWindrowWorkAreaIndex = Utils.getNoNil(getXMLInt(xmlFile, key .. ".windrower#dropWindrowWorkAreaIndex"), 1)
410
411 workArea.lastValidPickupFruitType = FruitType.UNKNOWN
412 workArea.lastPickupLiters = 0
413 workArea.lastDroppedLiters = 0
414 workArea.litersToDrop = 0
415
416 local spec = self.spec_windrower
417 if spec.windrowerWorkAreaFillTypes == nil then
418 spec.windrowerWorkAreaFillTypes = {}
419 end
420 table.insert(spec.windrowerWorkAreaFillTypes, FruitType.UNKNOWN)
421 workArea.windrowerWorkAreaIndex = #spec.windrowerWorkAreaFillTypes
422 end
423
424 return retValue
425end

onDeactivate

Description
Definition
onDeactivate()
Code
302function Windrower:onDeactivate()
303 if self.isClient then
304 local spec = self.spec_windrower
305 for _, effect in ipairs(spec.effects) do
306 g_effectManager:stopEffects(effect.effects)
307 end
308
309 if self.getIsTurnedOn == nil then
310 g_soundManager:stopSample(spec.samples.work)
311 spec.isWorking = false
312 end
313 end
314end

onDelete

Description
Definition
onDelete()
Code
156function Windrower:onDelete()
157 local spec = self.spec_windrower
158 if self.isClient then
159 for _,sample in pairs(spec.samples) do
160 g_soundManager:deleteSample(sample)
161 end
162 g_animationManager:deleteAnimations(spec.animationNodes)
163
164 for _, effect in ipairs(spec.effects) do
165 g_effectManager:deleteEffects(effect.effects)
166 end
167 end
168end

onEndWorkAreaProcessing

Description
Definition
onEndWorkAreaProcessing()
Code
469function Windrower:onEndWorkAreaProcessing(dt, workAreas)
470 local spec = self.spec_windrower
471
472 if self.isClient then
473 if self.getIsTurnedOn == nil then
474 if spec.isWorking then
475 if not g_soundManager:getIsSamplePlaying(spec.samples.work) then
476 g_soundManager:playSample(spec.samples.work)
477 end
478 else
479 if g_soundManager:getIsSamplePlaying(spec.samples.work) then
480 g_soundManager:stopSample(spec.samples.work)
481 end
482 end
483 end
484 end
485end

onLoad

Description
Definition
onLoad()
Code
62function Windrower:onLoad(savegame)
63 local spec = self.spec_windrower
64
65 XMLUtil.checkDeprecatedXMLElements(self.xmlFile, self.configFileName, "vehicle.animation", "vehicle.windrowers.windrower") --FS13 to FS15
66
67 XMLUtil.checkDeprecatedXMLElements(self.xmlFile, self.configFileName, "vehicle.windrowers.windrower", "vehicle.windrower.rakes.rake") --FS17 to FS19
68 XMLUtil.checkDeprecatedXMLElements(self.xmlFile, self.configFileName, "vehicle.windrowerParticleSystems", "vehicle.windrower.effects") --FS17 to FS19
69 XMLUtil.checkDeprecatedXMLElements(self.xmlFile, self.configFileName, "vehicle.turnedOnRotationNodes.turnedOnRotationNode#type", "vehicle.windrower.animationNodes.animationNode", "windrower") --FS17 to FS19
70 XMLUtil.checkDeprecatedXMLElements(self.xmlFile, self.configFileName, "vehicle.windrowerSound", "vehicle.windrower.sounds.work") --FS17 to FS19
71
72 if self.isClient then
73 spec.animationNodes = g_animationManager:loadAnimations(self.xmlFile, "vehicle.windrower.animationNodes", self.components, self, self.i3dMappings)
74
75 spec.effects = {}
76 spec.workAreaToEffects = {}
77 local i = 0
78 while true do
79 local key = string.format("vehicle.windrower.effects.effect(%d)", i)
80 if not hasXMLProperty(self.xmlFile, key) then
81 break
82 end
83 local effects = g_effectManager:loadEffect(self.xmlFile, key, self.components, self, self.i3dMappings)
84 if effects ~= nil then
85 local effect = {}
86 effect.effects = effects
87 effect.workAreaIndex = Utils.getNoNil(getXMLInt(self.xmlFile, key .. "#workAreaIndex"), 1)
88 effect.activeTime = -1
89 effect.activeTimeDuration = 250
90 effect.isActive = false
91 effect.isActiveSent = false
92 table.insert(spec.effects, effect)
93 end
94 i = i + 1
95 end
96
97 spec.rakes = {}
98 local i = 0
99 while true do
100 local key = string.format("vehicle.windrower.rakes.rake(%d)", i)
101 if not hasXMLProperty(self.xmlFile, key) then
102 break
103 end
104
105 local rake = {}
106 if self:loadRakeFromXML(rake, self.xmlFile, key, i) then
107 table.insert(spec.rakes, rake)
108 self:updateRake(rake)
109 end
110
111 i = i + 1
112 end
113
114 spec.samples = {}
115 spec.samples.work = g_soundManager:loadSampleFromXML(self.xmlFile, "vehicle.windrower.sounds", "work", self.baseDirectory, self.components, 0, AudioGroup.VEHICLE, self.i3dMappings, self)
116 end
117
118 spec.isWorking = false
119 spec.limitToLineHeight = Utils.getNoNil(getXMLBool(self.xmlFile, "vehicle.windrower#limitToLineHeight"), false)
120
121 spec.fillTypesDirtyFlag = self:getNextDirtyFlag()
122 spec.effectDirtyFlag = self:getNextDirtyFlag()
123
124 if self.addAIFruitRequirement ~= nil then
125 self:addAIFruitRequirement(FruitType.GRASS, 0, g_currentMission.terrainDetailHeightTypeNumChannels)
126 self:addAIFruitRequirement(FruitType.DRYGRASS, 0, g_currentMission.terrainDetailHeightTypeNumChannels)
127 self:addAIFruitRequirement(FruitType.WHEAT, 0, g_currentMission.terrainDetailHeightTypeNumChannels)
128 self:addAIFruitRequirement(FruitType.BARLEY, 0, g_currentMission.terrainDetailHeightTypeNumChannels)
129 self:setAIFruitExtraRequirements(true, true)
130 end
131end

onPostLoad

Description
Definition
onPostLoad()
Code
135function Windrower:onPostLoad(savegame)
136 local spec = self.spec_windrower
137 for i=#spec.effects, 1, -1 do
138 local effect = spec.effects[i]
139 local workArea = self:getWorkAreaByIndex(effect.workAreaIndex)
140 if workArea ~= nil then
141 effect.windrowerWorkAreaFillTypeIndex = workArea.windrowerWorkAreaIndex
142
143 if spec.workAreaToEffects[workArea.index] == nil then
144 spec.workAreaToEffects[workArea.index] = {}
145 end
146 table.insert(spec.workAreaToEffects[workArea.index], effect)
147 else
148 g_logManager:xmlWarning(self.xmlFileName, "Invalid workAreaIndex '%d' for effect 'vehicle.windrower.effects.effect(%d)'!", effect.workAreaIndex, i)
149 table.insert(spec.effects, i)
150 end
151 end
152end

onReadStream

Description
Definition
onReadStream()
Code
172function Windrower:onReadStream(streamId, connection)
173 local spec = self.spec_windrower
174 for index, _ in ipairs(spec.windrowerWorkAreaFillTypes) do
175 local fillType = streamReadUIntN(streamId, FillTypeManager.SEND_NUM_BITS)
176 spec.windrowerWorkAreaFillTypes[index] = fillType
177 end
178 for _, effect in ipairs(spec.effects) do
179 if streamReadBool(streamId) then
180 local fillType = spec.windrowerWorkAreaFillTypes[effect.windrowerWorkAreaFillTypeIndex]
181 g_effectManager:setFillType(effect.effects, fillType)
182 g_effectManager:startEffects(effect.effects)
183 else
184 g_effectManager:stopEffects(effect.effects)
185 end
186 end
187end

onReadUpdateStream

Description
Definition
onReadUpdateStream()
Code
203function Windrower:onReadUpdateStream(streamId, timestamp, connection)
204 if connection:getIsServer() then
205 local spec = self.spec_windrower
206
207 if streamReadBool(streamId) then
208 for index, _ in ipairs(spec.windrowerWorkAreaFillTypes) do
209 local fillType = streamReadUIntN(streamId, FillTypeManager.SEND_NUM_BITS)
210 spec.windrowerWorkAreaFillTypes[index] = fillType
211 end
212 end
213
214 if streamReadBool(streamId) then
215 for _, effect in ipairs(spec.effects) do
216 if streamReadBool(streamId) then
217 local fillType = spec.windrowerWorkAreaFillTypes[effect.windrowerWorkAreaFillTypeIndex]
218 g_effectManager:setFillType(effect.effects, fillType)
219 g_effectManager:startEffects(effect.effects)
220 else
221 g_effectManager:stopEffects(effect.effects)
222 end
223 end
224 end
225 end
226end

onStartWorkAreaProcessing

Description
Definition
onStartWorkAreaProcessing()
Code
457function Windrower:onStartWorkAreaProcessing(dt, workAreas)
458 local spec = self.spec_windrower
459 for _, workArea in pairs(workAreas) do
460 workArea.lastValidPickupFruitType = FruitType.UNKNOWN
461 workArea.lastPickupLiters = 0
462 workArea.lastDroppedLiters = 0
463 end
464 spec.isWorking = false
465end

onTurnedOff

Description
Definition
onTurnedOff()
Code
290function Windrower:onTurnedOff()
291 local spec = self.spec_windrower
292 g_soundManager:stopSamples(spec.samples)
293
294 for _, effect in ipairs(spec.effects) do
295 g_effectManager:stopEffects(effect.effects)
296 end
297 g_animationManager:stopAnimations(spec.animationNodes)
298end

onTurnedOn

Description
Definition
onTurnedOn()
Code
280function Windrower:onTurnedOn()
281 local spec = self.spec_windrower
282 if self.isClient then
283 g_soundManager:playSample(spec.samples.work)
284 g_animationManager:startAnimations(spec.animationNodes)
285 end
286end

onUpdateTick

Description
Definition
onUpdateTick()
Code
250function Windrower:onUpdateTick(dt, isActiveForInput, isActiveForInputIgnoreSelection, isSelected)
251 local spec = self.spec_windrower
252
253 if self.isServer then
254 for _, effect in ipairs(spec.effects) do
255 if effect.isActive and g_currentMission.time > effect.activeTime then
256 effect.isActive = false
257 if effect.isActiveSent then
258 effect.isActiveSent = false
259 self:raiseDirtyFlags(spec.effectDirtyFlag)
260 end
261 g_effectManager:stopEffects(effect.effects)
262 end
263 end
264 end
265
266 if self.isClient then
267 if g_animationManager:areAnimationsRunning(spec.animationNodes) then
268 for _, rake in pairs(spec.rakes) do
269 self:updateRake(rake)
270 end
271
272 -- raise active until the animations are faded out
273 self:raiseActive()
274 end
275 end
276end

onWriteStream

Description
Definition
onWriteStream()
Code
191function Windrower:onWriteStream(streamId, connection)
192 local spec = self.spec_windrower
193 for _, fillTypeIndex in ipairs(spec.windrowerWorkAreaFillTypes) do
194 streamWriteUIntN(streamId, fillTypeIndex, FillTypeManager.SEND_NUM_BITS)
195 end
196 for _, effect in ipairs(spec.effects) do
197 streamWriteBool(streamId, effect.isActiveSent)
198 end
199end

onWriteUpdateStream

Description
Definition
onWriteUpdateStream()
Code
230function Windrower:onWriteUpdateStream(streamId, connection, dirtyMask)
231 if not connection:getIsServer() then
232 local spec = self.spec_windrower
233
234 if streamWriteBool(streamId, bitAND(dirtyMask, spec.fillTypesDirtyFlag) ~= 0) then
235 for _, fillTypeIndex in ipairs(spec.windrowerWorkAreaFillTypes) do
236 streamWriteUIntN(streamId, fillTypeIndex, FillTypeManager.SEND_NUM_BITS)
237 end
238 end
239
240 if streamWriteBool(streamId, bitAND(dirtyMask, spec.effectDirtyFlag) ~= 0) then
241 for _, effect in ipairs(spec.effects) do
242 streamWriteBool(streamId, effect.isActiveSent)
243 end
244 end
245 end
246end

prerequisitesPresent

Description
Definition
prerequisitesPresent()
Code
21function Windrower.prerequisitesPresent(specializations)
22 return SpecializationUtil.hasSpecialization(WorkArea, specializations)
23end

processDropArea

Description
Definition
processDropArea()
Code
592function Windrower:processDropArea(dropArea, litersToDrop, fillType)
593 local lsx, lsy, lsz, lex, ley, lez, radius = DensityMapHeightUtil.getLineByArea(dropArea.start, dropArea.width, dropArea.height)
594 local dropped, lineOffset = DensityMapHeightUtil.tipToGroundAroundLine(self, litersToDrop, fillType, lsx,lsy,lsz, lex,ley,lez, radius, nil, dropArea.lineOffset, false, nil, false)
595 dropArea.lineOffset = lineOffset
596
597 return dropped
598end

processWindrowerArea

Description
Definition
processWindrowerArea()
Code
489function Windrower:processWindrowerArea(workArea, dt)
490 local spec = self.spec_windrower
491 local workAreaSpec = self.spec_workArea
492 spec.isWorking = self:getLastSpeed() > 0.5
493
494 -- pick up
495 local lsx, lsy, lsz, lex, ley, lez, radius = DensityMapHeightUtil.getLineByArea(workArea.start, workArea.width, workArea.height)
496
497 -- loop over all fruitTypes or use only lastValidPickupFruitType
498 local pickupLiters = 0
499 local pickupFruitType = FruitType.UNKNOWN
500 local lastValidFillType = g_fruitTypeManager:getFillTypeIndexByFruitTypeIndex(workArea.lastValidPickupFruitType)
501
502 if workArea.lastPickupLiters == 0 and (workArea.lastValidPickupFruitType == FruitType.UNKNOWN or workArea.litersToDrop < g_densityMapHeightManager:getMinValidLiterValue(lastValidFillType)) then
503 for fruitTypeIndex, _ in ipairs(g_fruitTypeManager:getFruitTypes()) do
504 local fillTypeIndex = g_fruitTypeManager:getWindrowFillTypeIndexByFruitTypeIndex(fruitTypeIndex)
505 if fillTypeIndex ~= nil then
506 pickupLiters = -DensityMapHeightUtil.tipToGroundAroundLine(self, -math.huge, fillTypeIndex, lsx,lsy,lsz, lex,ley,lez, radius, nil, nil, spec.limitToLineHeight, nil)
507 if pickupLiters > 0 then
508 pickupFruitType = fruitTypeIndex
509 break
510 end
511 end
512 end
513 else
514 pickupLiters = -DensityMapHeightUtil.tipToGroundAroundLine(self, -math.huge, g_fruitTypeManager:getWindrowFillTypeIndexByFruitTypeIndex(workArea.lastValidPickupFruitType), lsx,lsy,lsz, lex,ley,lez, radius, nil, nil, false, nil)
515
516 if workArea.lastValidPickupFruitType == FruitType.GRASS then
517 pickupLiters = pickupLiters - DensityMapHeightUtil.tipToGroundAroundLine(self, -math.huge, g_fruitTypeManager:getWindrowFillTypeIndexByFruitTypeIndex(FruitType.DRYGRASS), lsx,lsy,lsz, lex,ley,lez, radius, nil, nil, false, nil)
518 elseif workArea.lastValidPickupFruitType == FruitType.DRYGRASS then
519 pickupLiters = pickupLiters - DensityMapHeightUtil.tipToGroundAroundLine(self, -math.huge, g_fruitTypeManager:getWindrowFillTypeIndexByFruitTypeIndex(FruitType.GRASS), lsx,lsy,lsz, lex,ley,lez, radius, nil, nil, false, nil)
520 end
521
522 if pickupLiters > 0 then
523 pickupFruitType = workArea.lastValidPickupFruitType
524 end
525 end
526
527 if pickupFruitType ~= FruitType.UNKNOWN then
528 workArea.lastValidPickupFruitType = pickupFruitType
529 end
530 workArea.lastPickupLiters = pickupLiters
531 workArea.litersToDrop = workArea.litersToDrop + pickupLiters
532
533 --calculating area by area width multiplied by last moved distance (not 100% accuracy in corners)
534 local areaWidth = MathUtil.vector3Length(lsx-lex, lsy-ley, lsz-lez)
535 local area = areaWidth * self.lastMovedDistance
536
537 -- drop
538 if workArea.lastPickupLiters > 0 then
539 local dropArea = workAreaSpec.workAreas[workArea.dropWindrowWorkAreaIndex]
540 if dropArea ~= nil then
541 local dropType = g_fruitTypeManager:getWindrowFillTypeIndexByFruitTypeIndex(workArea.lastValidPickupFruitType)
542 local dropped = self:processDropArea(dropArea, workArea.lastPickupLiters, dropType)
543 workArea.lastDroppedLiters = dropped
544 workArea.litersToDrop = workArea.litersToDrop - dropped
545
546 if self.isServer then
547 --particles
548 if self:getLastSpeed(true) > 0.5 then
549 if dropped > 0 then
550 local changedFillType = false
551 if spec.windrowerWorkAreaFillTypes[workArea.windrowerWorkAreaIndex] ~= dropType then
552 spec.windrowerWorkAreaFillTypes[workArea.windrowerWorkAreaIndex] = dropType
553 self:raiseDirtyFlags(spec.fillTypesDirtyFlag)
554 changedFillType = true
555 end
556
557 local effects = spec.workAreaToEffects[workArea.index]
558 if effects ~= nil then
559 for _, effect in ipairs(effects) do
560 effect.activeTime = g_currentMission.time + effect.activeTimeDuration
561
562 -- sync mp
563 if not effect.isActiveSent then
564 effect.isActiveSent = true
565 self:raiseDirtyFlags(spec.effectDirtyFlag)
566 end
567
568 if changedFillType then
569 g_effectManager:setFillType(effect.effects, dropType)
570 end
571
572 -- enable effect
573 if not effect.isActive then
574 g_effectManager:setFillType(effect.effects, dropType)
575 g_effectManager:startEffects(effect.effects)
576 end
577
578 effect.isActive = true
579 end
580 end
581 end
582 end
583 end
584 end
585 end
586
587 return workArea.lastDroppedLiters, area
588end

registerEventListeners

Description
Definition
registerEventListeners()
Code
45function Windrower.registerEventListeners(vehicleType)
46 SpecializationUtil.registerEventListener(vehicleType, "onLoad", Windrower)
47 SpecializationUtil.registerEventListener(vehicleType, "onPostLoad", Windrower)
48 SpecializationUtil.registerEventListener(vehicleType, "onDelete", Windrower)
49 SpecializationUtil.registerEventListener(vehicleType, "onReadStream", Windrower)
50 SpecializationUtil.registerEventListener(vehicleType, "onWriteStream", Windrower)
51 SpecializationUtil.registerEventListener(vehicleType, "onReadUpdateStream", Windrower)
52 SpecializationUtil.registerEventListener(vehicleType, "onWriteUpdateStream", Windrower)
53 SpecializationUtil.registerEventListener(vehicleType, "onUpdateTick", Windrower)
54 SpecializationUtil.registerEventListener(vehicleType, "onTurnedOn", Windrower)
55 SpecializationUtil.registerEventListener(vehicleType, "onTurnedOff", Windrower)
56 SpecializationUtil.registerEventListener(vehicleType, "onStartWorkAreaProcessing", Windrower)
57 SpecializationUtil.registerEventListener(vehicleType, "onEndWorkAreaProcessing", Windrower)
58end

registerFunctions

Description
Definition
registerFunctions()
Code
27function Windrower.registerFunctions(vehicleType)
28 SpecializationUtil.registerFunction(vehicleType, "loadRakeFromXML", Windrower.loadRakeFromXML)
29 SpecializationUtil.registerFunction(vehicleType, "updateRake", Windrower.updateRake)
30 SpecializationUtil.registerFunction(vehicleType, "processWindrowerArea", Windrower.processWindrowerArea)
31 SpecializationUtil.registerFunction(vehicleType, "processDropArea", Windrower.processDropArea)
32end

registerOverwrittenFunctions

Description
Definition
registerOverwrittenFunctions()
Code
36function Windrower.registerOverwrittenFunctions(vehicleType)
37 SpecializationUtil.registerOverwrittenFunction(vehicleType, "doCheckSpeedLimit", Windrower.doCheckSpeedLimit)
38 SpecializationUtil.registerOverwrittenFunction(vehicleType, "loadWorkAreaFromXML", Windrower.loadWorkAreaFromXML)
39 SpecializationUtil.registerOverwrittenFunction(vehicleType, "getDirtMultiplier", Windrower.getDirtMultiplier)
40 SpecializationUtil.registerOverwrittenFunction(vehicleType, "getWearMultiplier", Windrower.getWearMultiplier)
41end

updateRake

Description
Definition
updateRake()
Code
369function Windrower:updateRake(rake)
370 local _,y,_ = getRotation(rake.node)
371 y = y % (2*math.pi)
372 if rake.dir == -1 then
373 y = math.abs(2*math.pi-y)
374 end
375
376 for k, spike in pairs(rake.spikes) do
377 local yRot = ((y - (k-1)*rake.yRotOffset) + 2*math.pi) % (2*math.pi)
378 local alpha = 0
379
380 if yRot > rake.moveUpStart and yRot <= rake.moveUpEnd then
381 alpha = 1 - (rake.moveUpEnd-yRot) / (rake.moveUpEnd-rake.moveUpStart)
382 elseif yRot > rake.moveDownStart and yRot <= rake.moveDownEnd then
383 alpha = ((rake.moveDownEnd-yRot) / (rake.moveDownEnd-rake.moveDownStart))
384 elseif yRot > rake.moveUpEnd and yRot <= rake.moveDownStart then
385 alpha = 1
386 end
387
388 setRotation(spike.node, 0, 0, rake.maxRotZ*alpha*spike.dir)
389 end
390end