371 | function PlaceableHusbandry:collectPickObjects(superFunc, node, target) |
372 | local spec = self.spec_husbandry |
373 | |
374 | if spec.unloadingStation ~= nil then |
375 | for _, unloadTrigger in ipairs(spec.unloadingStation.unloadTriggers) do |
376 | if node == unloadTrigger.exactFillRootNode then |
377 | return |
378 | end |
379 | end |
380 | end |
381 | |
382 | if spec.loadingStation ~= nil then |
383 | for _, loadTrigger in ipairs(spec.loadingStation.loadTriggers) do |
384 | if node == loadTrigger.triggerNode then |
385 | return |
386 | end |
387 | end |
388 | end |
389 | |
390 | superFunc(self, node, target) |
391 | end |
164 | function PlaceableHusbandry:onDelete() |
165 | local spec = self.spec_husbandry |
166 | |
167 | local storageSystem = g_currentMission.storageSystem |
168 | |
169 | if spec.unloadingStation ~= nil then |
170 | storageSystem:removeStorageFromUnloadingStations(spec.storage, {spec.unloadingStation}) |
171 | storageSystem:removeUnloadingStation(spec.unloadingStation, self) |
172 | spec.unloadingStation:delete() |
173 | spec.unloadingStation = nil |
174 | end |
175 | if spec.loadingStation ~= nil then |
176 | if spec.loadingStation:getIsFillTypeSupported(FillType.LIQUIDMANURE) then |
177 | g_currentMission:removeLiquidManureLoadingStation(spec.loadingStation) |
178 | end |
179 | |
180 | storageSystem:removeStorageFromLoadingStations(spec.storage, {spec.loadingStation}) |
181 | storageSystem:removeLoadingStation(spec.loadingStation, self) |
182 | spec.loadingStation:delete() |
183 | spec.loadingStation = nil |
184 | end |
185 | if spec.storage ~= nil then |
186 | storageSystem:removeStorage(spec.storage) |
187 | spec.storage:delete() |
188 | spec.storage = nil |
189 | end |
190 | |
191 | g_messageCenter:unsubscribe(MessageType.STORAGE_ADDED_TO_LOADING_STATION, self) |
192 | g_messageCenter:unsubscribe(MessageType.STORAGE_REMVOED_FROM_LOADING_STATION, self) |
193 | g_messageCenter:unsubscribe(MessageType.STORAGE_ADDED_TO_UNLOADING_STATION, self) |
194 | g_messageCenter:unsubscribe(MessageType.STORAGE_REMVOED_FROM_UNLOADING_STATION, self) |
195 | |
196 | g_currentMission.husbandrySystem:removePlaceable(self) |
197 | end |
201 | function PlaceableHusbandry:onFinalizePlacement() |
202 | local spec = self.spec_husbandry |
203 | |
204 | g_messageCenter:subscribe(MessageType.STORAGE_ADDED_TO_LOADING_STATION, self.onAddedStorageToLoadingStation, self) |
205 | g_messageCenter:subscribe(MessageType.STORAGE_REMOVED_FROM_LOADING_STATION, self.onRemovedStorageFromLoadingStation, self) |
206 | g_messageCenter:subscribe(MessageType.STORAGE_ADDED_TO_UNLOADING_STATION, self.onAddedStorageToUnloadingStation, self) |
207 | g_messageCenter:subscribe(MessageType.STORAGE_REMOVED_FROM_UNLOADING_STATION, self.onRemovedStorageFromUnloadingStation, self) |
208 | |
209 | local storage = spec.storage |
210 | local unloadingStation = spec.unloadingStation |
211 | local storageSystem = g_currentMission.storageSystem |
212 | local loadingStation = spec.loadingStation |
213 | local farmId = self:getOwnerFarmId() |
214 | |
215 | if loadingStation ~= nil then |
216 | loadingStation:setOwnerFarmId(farmId, true) |
217 | loadingStation:register(true) |
218 | storageSystem:addLoadingStation(loadingStation, self) |
219 | |
220 | if loadingStation:getIsFillTypeSupported(FillType.LIQUIDMANURE) then |
221 | g_currentMission:addLiquidManureLoadingStation(loadingStation) |
222 | end |
223 | end |
224 | |
225 | if unloadingStation ~= nil then |
226 | unloadingStation:setOwnerFarmId(farmId, true) |
227 | unloadingStation:register(true) |
228 | storageSystem:addUnloadingStation(unloadingStation, self) |
229 | end |
230 | |
231 | if storage ~= nil then |
232 | storage:setOwnerFarmId(farmId, true) |
233 | storage:register(true) |
234 | storageSystem:addStorage(storage) |
235 | |
236 | if unloadingStation ~= nil then |
237 | storageSystem:addStorageToUnloadingStation(storage, unloadingStation) |
238 | end |
239 | |
240 | if loadingStation ~= nil then |
241 | storageSystem:addStorageToLoadingStation(storage, loadingStation) |
242 | end |
243 | end |
244 | |
245 | |
246 | if unloadingStation ~= nil then |
247 | -- now check if there are some storages in range which can also be used |
248 | local storagesInRange = storageSystem:getStorageExtensionsInRange(unloadingStation, farmId) |
249 | for _, storageInRange in ipairs(storagesInRange) do |
250 | if unloadingStation.targetStorages[storageInRange] == nil then |
251 | storageSystem:addStorageToUnloadingStation(storageInRange, unloadingStation) |
252 | end |
253 | if loadingStation ~= nil and loadingStation.sourceStorages[storageInRange] == nil then |
254 | storageSystem:addStorageToLoadingStation(storageInRange, loadingStation) |
255 | end |
256 | end |
257 | end |
258 | |
259 | g_currentMission.husbandrySystem:addPlaceable(self) |
260 | end |
415 | function PlaceableHusbandry:onHourChanged(currentHour) |
416 | if self.isServer then |
417 | local spec = self.spec_husbandry |
418 | local foodFactor = self:updateFeeding() |
419 | local productionFactor = self:updateProduction(foodFactor) |
420 | |
421 | local factor |
422 | local changePerHour |
423 | if productionFactor > spec.productionThreshold then |
424 | factor = (productionFactor - spec.productionThreshold) / (1 - spec.productionThreshold) |
425 | changePerHour = spec.productionChangePerHourIncrease |
426 | else |
427 | factor = (productionFactor / spec.productionThreshold) - 1 |
428 | changePerHour = spec.productionChangePerHourDecrease |
429 | end |
430 | |
431 | local delta = changePerHour*factor |
432 | spec.globalProductionFactor = MathUtil.clamp(spec.globalProductionFactor + delta, 0, 1) |
433 | |
434 | self:updateOutput(foodFactor, productionFactor, spec.globalProductionFactor) |
435 | self:raiseDirtyFlags(spec.dirtyFlag) |
436 | end |
437 | end |
102 | function PlaceableHusbandry:onLoad(savegame) |
103 | local spec = self.spec_husbandry |
104 | local xmlFile = self.xmlFile |
105 | |
106 | spec.fillLevelChangedListener = {} |
107 | spec.targetStorages = {} |
108 | spec.hideFromPricesMenu = true |
109 | -- spec.saveId = xmlFile:getValue("placeable.husbandry#saveId", "Animals_" .. self:getAnimalType()) |
110 | -- spec.hasStatistics = xmlFile:getValue("placeable.husbandry#hasStatistics", spec.hasStatistics) |
111 | spec.globalProductionFactor = 0.0 |
112 | |
113 | spec.husbandryDirtyFlag = self:getNextDirtyFlag() |
114 | |
115 | if xmlFile:hasProperty("placeable.husbandry.unloadingStation") then |
116 | spec.unloadingStation = UnloadingStation.new(self.isServer, self.isClient) |
117 | if spec.unloadingStation:load(self.components, xmlFile, "placeable.husbandry.unloadingStation", self.customEnvironment, self.i3dMappings, self.components[1].node) then |
118 | spec.unloadingStation.owningPlaceable = self |
119 | spec.unloadingStation.hasStoragePerFarm = false |
120 | else |
121 | spec.unloadingStation:delete() |
122 | Logging.xmlError(xmlFile, "Failed to load unloading station") |
123 | self:setLoadingState(Placeable.LOADING_STATE_ERROR) |
124 | return |
125 | end |
126 | end |
127 | |
128 | if xmlFile:hasProperty("placeable.husbandry.storage") then |
129 | spec.storage = Storage.new(self.isServer, self.isClient) |
130 | if not spec.storage:load(self.components, xmlFile, "placeable.husbandry.storage", self.i3dMappings) then |
131 | spec.storage:delete() |
132 | Logging.xmlError(xmlFile, "Failed to load storage") |
133 | self:setLoadingState(Placeable.LOADING_STATE_ERROR) |
134 | return |
135 | end |
136 | end |
137 | |
138 | if xmlFile:hasProperty("placeable.husbandry.loadingStation") then |
139 | spec.loadingStation = LoadingStation.new(self.isServer, self.isClient) |
140 | if spec.loadingStation:load(self.components, xmlFile, "placeable.husbandry.loadingStation", self.customEnvironment, self.i3dMappings, self.components[1].node) then |
141 | spec.loadingStation.owningPlaceable = self |
142 | spec.loadingStation.hasStoragePerFarm = false |
143 | else |
144 | spec.loadingStation:delete() |
145 | Logging.xmlError(xmlFile, "Failed to load loading station") |
146 | self:setLoadingState(Placeable.LOADING_STATE_ERROR) |
147 | return |
148 | end |
149 | end |
150 | |
151 | spec.fillLevelChangedCallback = function(fillType, delta) |
152 | SpecializationUtil.raiseEvent(self, "onHusbandryFillLevelChanged", fillType, delta) |
153 | end |
154 | |
155 | spec.productionThreshold = MathUtil.clamp(math.abs(xmlFile:getValue("placeable.husbandry.production#threshold", 0.5)), 0.01, 0.99) |
156 | spec.productionChangePerHourIncrease = math.abs(xmlFile:getValue("placeable.husbandry.production#increasePerHour", 0.1)) |
157 | spec.productionChangePerHourDecrease = math.abs(xmlFile:getValue("placeable.husbandry.production#decreasePerHour", 0.2)) |
158 | |
159 | spec.dirtyFlag = self:getNextDirtyFlag() |
160 | end |
264 | function PlaceableHusbandry:onReadStream(streamId, connection) |
265 | local spec = self.spec_husbandry |
266 | |
267 | if spec.unloadingStation ~= nil then |
268 | local unloadingStationId = NetworkUtil.readNodeObjectId(streamId) |
269 | spec.unloadingStation:readStream(streamId, connection) |
270 | g_client:finishRegisterObject(spec.unloadingStation, unloadingStationId) |
271 | end |
272 | |
273 | if spec.loadingStation ~= nil then |
274 | local loadingStationId = NetworkUtil.readNodeObjectId(streamId) |
275 | spec.loadingStation:readStream(streamId, connection) |
276 | g_client:finishRegisterObject(spec.loadingStation, loadingStationId) |
277 | end |
278 | |
279 | if spec.storage ~= nil then |
280 | local storageId = NetworkUtil.readNodeObjectId(streamId) |
281 | spec.storage:readStream(streamId, connection) |
282 | g_client:finishRegisterObject(spec.storage, storageId) |
283 | end |
284 | |
285 | spec.globalProductionFactor = streamReadUInt8(streamId) / 255 |
286 | end |
290 | function PlaceableHusbandry:onWriteStream(streamId, connection) |
291 | local spec = self.spec_husbandry |
292 | |
293 | if spec.unloadingStation ~= nil then |
294 | NetworkUtil.writeNodeObjectId(streamId, NetworkUtil.getObjectId(spec.unloadingStation)) |
295 | spec.unloadingStation:writeStream(streamId, connection) |
296 | g_server:registerObjectInStream(connection, spec.unloadingStation) |
297 | end |
298 | |
299 | if spec.loadingStation ~= nil then |
300 | NetworkUtil.writeNodeObjectId(streamId, NetworkUtil.getObjectId(spec.loadingStation)) |
301 | spec.loadingStation:writeStream(streamId, connection) |
302 | g_server:registerObjectInStream(connection, spec.loadingStation) |
303 | end |
304 | |
305 | if spec.storage ~= nil then |
306 | NetworkUtil.writeNodeObjectId(streamId, NetworkUtil.getObjectId(spec.storage)) |
307 | spec.storage:writeStream(streamId, connection) |
308 | g_server:registerObjectInStream(connection, spec.storage) |
309 | end |
310 | |
311 | streamWriteUInt8(streamId, MathUtil.round(spec.globalProductionFactor * 255)) |
312 | end |
63 | function PlaceableHusbandry.registerEventListeners(placeableType) |
64 | SpecializationUtil.registerEventListener(placeableType, "onLoad", PlaceableHusbandry) |
65 | SpecializationUtil.registerEventListener(placeableType, "onDelete", PlaceableHusbandry) |
66 | SpecializationUtil.registerEventListener(placeableType, "onFinalizePlacement", PlaceableHusbandry) |
67 | SpecializationUtil.registerEventListener(placeableType, "onReadStream", PlaceableHusbandry) |
68 | SpecializationUtil.registerEventListener(placeableType, "onWriteStream", PlaceableHusbandry) |
69 | SpecializationUtil.registerEventListener(placeableType, "onReadUpdateStream", PlaceableHusbandry) |
70 | SpecializationUtil.registerEventListener(placeableType, "onWriteUpdateStream", PlaceableHusbandry) |
71 | SpecializationUtil.registerEventListener(placeableType, "onHourChanged", PlaceableHusbandry) |
72 | end |
30 | function PlaceableHusbandry.registerFunctions(placeableType) |
31 | SpecializationUtil.registerFunction(placeableType, "onAddedStorageToLoadingStation", PlaceableHusbandry.onAddedStorageToLoadingStation) |
32 | SpecializationUtil.registerFunction(placeableType, "onRemovedStorageFromLoadingStation", PlaceableHusbandry.onRemovedStorageFromLoadingStation) |
33 | SpecializationUtil.registerFunction(placeableType, "onAddedStorageToUnloadingStation", PlaceableHusbandry.onAddedStorageToUnloadingStation) |
34 | SpecializationUtil.registerFunction(placeableType, "onRemovedStorageFromUnloadingStation", PlaceableHusbandry.onRemovedStorageFromUnloadingStation) |
35 | SpecializationUtil.registerFunction(placeableType, "updateFeeding", PlaceableHusbandry.updateFeeding) |
36 | SpecializationUtil.registerFunction(placeableType, "updateProduction", PlaceableHusbandry.updateProduction) |
37 | SpecializationUtil.registerFunction(placeableType, "updateOutput", PlaceableHusbandry.updateOutput) |
38 | SpecializationUtil.registerFunction(placeableType, "getGlobalProductionFactor", PlaceableHusbandry.getGlobalProductionFactor) |
39 | SpecializationUtil.registerFunction(placeableType, "getConditionInfos", PlaceableHusbandry.getConditionInfos) |
40 | SpecializationUtil.registerFunction(placeableType, "getFoodInfos", PlaceableHusbandry.getFoodInfos) |
41 | SpecializationUtil.registerFunction(placeableType, "getAnimalInfos", PlaceableHusbandry.getAnimalInfos) |
42 | SpecializationUtil.registerFunction(placeableType, "getAnimalDescription", PlaceableHusbandry.getAnimalDescription) |
43 | SpecializationUtil.registerFunction(placeableType, "getHusbandryCapacity", PlaceableHusbandry.getHusbandryCapacity) |
44 | SpecializationUtil.registerFunction(placeableType, "getHusbandryFreeCapacity", PlaceableHusbandry.getHusbandryFreeCapacity) |
45 | SpecializationUtil.registerFunction(placeableType, "addHusbandryFillLevelFromTool", PlaceableHusbandry.addHusbandryFillLevelFromTool) |
46 | SpecializationUtil.registerFunction(placeableType, "removeHusbandryFillLevel", PlaceableHusbandry.removeHusbandryFillLevel) |
47 | SpecializationUtil.registerFunction(placeableType, "getHusbandryFillLevel", PlaceableHusbandry.getHusbandryFillLevel) |
48 | SpecializationUtil.registerFunction(placeableType, "getHusbandryIsFillTypeSupported", PlaceableHusbandry.getHusbandryIsFillTypeSupported) |
49 | end |
76 | function PlaceableHusbandry.registerXMLPaths(schema, basePath) |
77 | schema:setXMLSpecializationType("Husbandry") |
78 | schema:register(XMLValueType.STRING, basePath .. ".husbandry#saveId", "Save id") |
79 | schema:register(XMLValueType.BOOL, basePath .. ".husbandry#hasStatistics", "Has statistics", false) |
80 | schema:register(XMLValueType.FLOAT, basePath .. ".husbandry.production#threshold", "Threshold for production increase", 0.5) |
81 | schema:register(XMLValueType.FLOAT, basePath .. ".husbandry.production#increasePerHour", "Production increase if production factor bigger then threshold", 0.1) |
82 | schema:register(XMLValueType.FLOAT, basePath .. ".husbandry.production#decreasePerHour", "Production increase if production factor less then threshold", 0.2) |
83 | UnloadingStation.registerXMLPaths(schema, basePath .. ".husbandry.unloadingStation") |
84 | Storage.registerXMLPaths(schema, basePath .. ".husbandry.storage") |
85 | LoadingStation.registerXMLPaths(schema, basePath .. ".husbandry.loadingStation") |
86 | schema:setXMLSpecializationType() |
87 | end |
353 | function PlaceableHusbandry:setOwnerFarmId(superFunc, farmId, noEventSend) |
354 | local spec = self.spec_husbandry |
355 | |
356 | superFunc(self, farmId, noEventSend) |
357 | |
358 | if spec.storage ~= nil then |
359 | spec.storage:setOwnerFarmId(farmId, true) |
360 | end |
361 | if spec.loadingStation ~= nil then |
362 | spec.loadingStation:setOwnerFarmId(farmId, true) |
363 | end |
364 | if spec.unloadingStation ~= nil then |
365 | spec.unloadingStation:setOwnerFarmId(farmId, true) |
366 | end |
367 | end |