Sprache Deutsch Language English

Script Dokumentation LS 2015 - SiloTrigger (Patch 1.3)

Script Dokumentation Übersicht

scripts/triggers/SiloTrigger.lua

Copyright (c) 2008-2015 GIANTS Software GmbH, Confidential, All Rights Reserved.
This document is to be published solely by ls-mods.de
1-- Copyright (C) GIANTS Software GmbH, Confidential, All Rights Reserved.
2
3SiloTrigger = {};
4
5local SiloTrigger_mt = Class(SiloTrigger, Object);
6
7InitStaticObjectClass(SiloTrigger, "SiloTrigger", ObjectIds.OBJECT_SILO_TRIGGER);
8
9function SiloTrigger:onCreate(id)
10 local trigger = SiloTrigger:new(g_server ~= nil, g_client ~= nil);
11 local index = g_currentMission:addOnCreateLoadedObject(trigger);
12 trigger:load(id);
13 trigger:register(true);
14 --[[if g_client ~= nil then
15 -- request server id from server
16 g_client:getServerConnection():sendEvent(OnCreateLoadedObjectEvent:new(index));
17 end;]]
18end;
19
20function SiloTrigger:new(isServer, isClient)
21 local self = Object:new(isServer, isClient, SiloTrigger_mt);
22 self.rootNode = 0;
23
24 self.siloTriggerDirtyFlag = self:getNextDirtyFlag();
25 return self;
26end;
27
28
29function SiloTrigger:load(id)
30
31 self.rootNode = id;
32 if self.isServer then
33 self.triggerIds = {};
34
35 local triggerRoot = Utils.indexToObject(id, getUserAttribute(id, "triggerIndex"));
36 if triggerRoot == nil then
37 triggerRoot = id;
38 end
39
40 table.insert(self.triggerIds, triggerRoot);
41 addTrigger(triggerRoot, "triggerCallback", self);
42 for i=1, 3 do
43 local child = getChildAt(triggerRoot, i-1);
44 table.insert(self.triggerIds, child);
45 addTrigger(child, "triggerCallback", self);
46 end;
47 end;
48
49 self.fillVolumeDischargeInfo = {};
50 self.fillVolumeDischargeInfo.name = "fillVolumeDischargeInfo";
51 self.fillVolumeDischargeInfo.node = Utils.indexToObject(id, getUserAttribute(id, "fillVolumeDischargeNode"));
52 self.fillVolumeDischargeInfo.width = Utils.getNoNil( getUserAttribute(id, "fillVolumeDischargeNodeWidth"), 0.5 );
53 self.fillVolumeDischargeInfo.length = Utils.getNoNil( getUserAttribute(id, "fillVolumeDischargeNodeLength"), 0.5 );
54
55 self.fillType = Fillable.FILLTYPE_UNKNOWN;
56 local fruitType = getUserAttribute(id, "fruitType");
57 if fruitType ~= nil then
58 local desc = FruitUtil.fruitTypes[fruitType];
59 if desc ~= nil then
60 self.fillType = FruitUtil.fruitTypeToFillType[desc.index];
61 end;
62 elseif Utils.getNoNil(getUserAttribute(id, "fillTypeWheat"), false) then
63 self.fillType = Fillable.FILLTYPE_WHEAT;
64 elseif Utils.getNoNil(getUserAttribute(id, "fillTypeGrass"), false) then
65 self.fillType = Fillable.FILLTYPE_GRASS;
66 end;
67
68 self.isEnabled = true;
69
70 self.fill = 0;
71 self.siloTrailer = nil;
72 self.fillDone = false;
73
74 self.isFilling = false;
75
76 self.fillLitersPerSecond = Utils.getNoNil(tonumber(getUserAttribute(id, "fillLitersPerSecond")), 1500);
77
78 if self.isClient then
79 local dropParticleSystem = Utils.indexToObject(id, getUserAttribute(id, "dropParticleSystemIndex"));
80 if dropParticleSystem ~= nil then
81 self.dropParticleSystems = {};
82 Utils.loadParticleSystemFromNode(dropParticleSystem, self.dropParticleSystems, false, true);
83 end
84 local lyingParticleSystem = Utils.indexToObject(id, getUserAttribute(id, "lyingParticleSystemIndex"));
85 if lyingParticleSystem ~= nil then
86 self.lyingParticleSystems = {};
87 Utils.loadParticleSystemFromNode(lyingParticleSystem, self.lyingParticleSystems, true, true);
88
89 for _, ps in ipairs(self.lyingParticleSystems) do
90 local lifespan = getParticleSystemLifespan(ps.geometry);
91 addParticleSystemSimulationTime(ps.geometry, lifespan);
92 end
93
94 Utils.setParticleSystemTimeScale(self.lyingParticleSystems, 0);
95 end
96
97 if self.dropParticleSystems == nil then
98 local particleSystem = Utils.getNoNil(getUserAttribute(id, "particleSystem"), "wheatParticleSystemLong");
99
100 local x,y,z = getTranslation(id);
101
102 local particlePositionStr = getUserAttribute(id, "particlePosition");
103 if particlePositionStr ~= nil then
104 local psx,psy,psz = Utils.getVectorFromString(particlePositionStr);
105 if psx ~= nil and psy ~= nil and psz ~= nil then
106 x = x + psx;
107 y = y + psy;
108 z = z + psz;
109 end;
110 end;
111
112 local psData = {};
113 psData.psFile = getUserAttribute(id, "particleSystemFilename");
114 if psData.psFile == nil then
115 local particleSystem = Utils.getNoNil(getUserAttribute(id, "particleSystem"), "wheatParticleSystemLong");
116 psData.psFile = "$data/vehicles/particleSystems/" .. particleSystem .. ".i3d";
117 end
118 psData.posX, psData.posY, psData.posZ = x,y,z;
119 psData.forceNoWorldSpace = true;
120
121 self.dropParticleSystems = {};
122 Utils.loadParticleSystemFromData(psData, self.dropParticleSystems, nil, false, nil, g_currentMission.baseDirectory, getParent(id));
123 end
124
125 local fillSoundFilename = getUserAttribute(id, "fillSoundFilename");
126 if fillSoundFilename == nil then
127 fillSoundFilename = "$data/maps/sounds/siloFillSound.wav";
128 end
129 if fillSoundFilename ~= "" and fillSoundFilename ~= "none" then
130 fillSoundFilename = Utils.getFilename(fillSoundFilename, g_currentMission.baseDirectory);
131 self.siloFillSound = createAudioSource("siloFillSound", fillSoundFilename, 30, 10, 1, 0);
132 link(id, self.siloFillSound);
133 setVisibility(self.siloFillSound, false);
134 end
135
136
137 self.scroller = Utils.indexToObject(id, getUserAttribute(id, "scrollerIndex"));
138 if self.scroller ~= nil then
139 self.scrollerShaderParameterName = Utils.getNoNil(getUserAttribute(self.scroller, "shaderParameterName"), "uvScrollSpeed");
140 local scrollerScrollSpeed = getUserAttribute(self.scroller, "scrollSpeed");
141 if scrollerScrollSpeed ~= nil then
142 self.scrollerSpeedX, self.scrollerSpeedY = Utils.getVectorFromString(scrollerScrollSpeed);
143 end
144 if self.scrollerSpeedX == nil then
145 self.scrollerSpeedX = 0;
146 end
147 if self.scrollerSpeedY == nil then
148 self.scrollerSpeedY = -0.75;
149 end
150 setShaderParameter(self.scroller, self.scrollerShaderParameterName, 0, 0, 0, 0, false);
151 end
152 end;
153end;
154
155function SiloTrigger:delete()
156
157 if self.isClient then
158 if self.siloFillSound ~= nil then
159 delete(self.siloFillSound);
160 end
161
162 Utils.deleteParticleSystem(self.dropParticleSystems);
163 Utils.deleteParticleSystem(self.lyingParticleSystems);
164 end
165
166 if self.isServer then
167 for i=1, table.getn(self.triggerIds) do
168 removeTrigger(self.triggerIds[i]);
169 end
170 end
171
172 delete(self.rootNode);
173 SiloTrigger:superClass().delete(self);
174end;
175
176function SiloTrigger:readStream(streamId, connection)
177 SiloTrigger:superClass().readStream(self, streamId);
178 if connection:getIsServer() then
179 local isFilling = streamReadBool(streamId);
180 if isFilling then
181 self:startFill();
182 else
183 self:stopFill();
184 end;
185 end;
186end;
187
188function SiloTrigger:writeStream(streamId, connection)
189 SiloTrigger:superClass().writeStream(self, streamId);
190 if not connection:getIsServer() then
191 streamWriteBool(streamId, self.isFilling);
192 end;
193end;
194
195function SiloTrigger:readUpdateStream(streamId, timestamp, connection)
196 SiloTrigger:superClass().readUpdateStream(self, streamId, timestamp, connection);
197 if connection:getIsServer() then
198 local isFilling = streamReadBool(streamId);
199 if isFilling then
200 self:startFill();
201 else
202 self:stopFill();
203 end;
204 end;
205end;
206
207function SiloTrigger:writeUpdateStream(streamId, connection, dirtyMask)
208 SiloTrigger:superClass().writeUpdateStream(self, streamId, connection, dirtyMask);
209 if not connection:getIsServer() then
210 -- note: do not test for the dirty flags, since we only send 1 bit
211 streamWriteBool(streamId, self.isFilling);
212 end;
213end;
214
215function SiloTrigger:update(dt)
216
217 if self.isServer then
218 local trailer = self.siloTrailer;
219 if self.fill >= 4 and trailer ~= nil and not self.fillDone then
220 trailer:resetFillLevelIfNeeded(self.fillType);
221 local fillLevel = trailer:getFillLevel(self.fillType);
222 local siloAmount = g_currentMission:getSiloAmount(self.fillType);
223 if siloAmount > 0 and trailer:allowFillType(self.fillType, false) then
224 local deltaFillLevel = math.min(self.fillLitersPerSecond*0.001*dt, siloAmount);
225 local x,y,z = getWorldTranslation(self.fillVolumeDischargeInfo.node);
226 local d1x,d1y,d1z = localDirectionToWorld(self.fillVolumeDischargeInfo.node, self.fillVolumeDischargeInfo.width,0,0);
227 local d2x,d2y,d2z = localDirectionToWorld(self.fillVolumeDischargeInfo.node, 0,0,self.fillVolumeDischargeInfo.length);
228 local fillSourceStruct = {x=x,y=y,z=z, d1x=d1x,d1y=d1y,d1z=d1z, d2x=d2x,d2y=d2y,d2z=d2z};
229 trailer:setFillLevel(fillLevel+deltaFillLevel, self.fillType, false, fillSourceStruct);
230 local newFillLevel = trailer:getFillLevel(self.fillType);
231
232 if fillLevel ~= newFillLevel then
233 g_currentMission:setSiloAmount(self.fillType, math.max(siloAmount-(newFillLevel-fillLevel), 0));
234 self:startFill();
235 else
236 self.fillDone = true; -- trailer is full
237 self:stopFill();
238 end;
239
240 else
241 self.fillDone = true; -- silo is empty or trailer does not support fill type
242 self:stopFill();
243 end;
244 end;
245 end;
246
247end;
248
249function SiloTrigger:stopFill()
250 --print("stopFill");
251 if self.isFilling then
252 self.isFilling = false;
253 if self.isServer then
254 self:raiseDirtyFlags(self.siloTriggerDirtyFlag);
255 end;
256 if self.isClient then
257 if self.siloFillSoundEnabled then
258 setVisibility(self.siloFillSound, false);
259 self.siloFillSoundEnabled = false;
260 end;
261 Utils.setEmittingState(self.dropParticleSystems, false);
262 Utils.setParticleSystemTimeScale(self.lyingParticleSystems, 0);
263 if self.scroller ~= nil then
264 setShaderParameter(self.scroller, self.scrollerShaderParameterName, 0, 0, 0, 0, false);
265 end
266 end;
267 end;
268end;
269
270function SiloTrigger:startFill()
271 --print("startFill");
272 if not self.isFilling then
273 self.isFilling = true;
274 if self.isServer then
275 self:raiseDirtyFlags(self.siloTriggerDirtyFlag);
276 end;
277 if self.isClient then
278 if not self.siloFillSoundEnabled and self.siloFillSound ~= nil then
279 setVisibility(self.siloFillSound, true);
280 self.siloFillSoundEnabled = true;
281 end;
282 Utils.setEmittingState(self.dropParticleSystems, true);
283 Utils.setParticleSystemTimeScale(self.lyingParticleSystems, 1.0);
284
285 if self.scroller ~= nil then
286 setShaderParameter(self.scroller, self.scrollerShaderParameterName, self.scrollerSpeedX, self.scrollerSpeedY, 0, 0, false);
287 end
288 end;
289 end;
290end;
291
292function SiloTrigger:triggerCallback(triggerId, otherActorId, onEnter, onLeave, onStay, otherShapeId)
293
294 assert(self.isServer);
295 if self.isEnabled then
296 local trailer = g_currentMission.objectToTrailer[otherShapeId];
297 if trailer ~= nil and trailer:allowFillType(self.fillType, false) and trailer.getAllowFillFromAir ~= nil and trailer:getAllowFillFromAir() then
298 if onEnter then
299 self.fill = self.fill+1;
300 self.siloTrailer = trailer;
301 self.fillDone = false;
302 elseif onLeave then
303 self.fill = math.max(self.fill-1, 0);
304 self.siloTrailer = nil;
305 self.fillDone = false;
306 self:stopFill();
307 end;
308 end;
309 end;
310end;
Copyright (c) 2008-2015 GIANTS Software GmbH, Confidential, All Rights Reserved.
This document is to be published solely by ls-mods.de
Script Dokumentation Übersicht