]> git.somenet.org - factorio/Waterbomb.git/blob - control.lua
gitify, so I dont delete my stuff again.
[factorio/Waterbomb.git] / control.lua
1 \r
2 --[[added by someone1337: water-creation + displace dirt radius]]\r
3 local explosionRadius = 3\r
4 \r
5 local displaceDirt = false\r
6 local throwRocksIntoWater = false\r
7 local throwRocks = true\r
8 local maximumRockThrowDistance = explosionRadius + 9\r
9 local bombs\r
10 local replaceableTiles =\r
11 {\r
12   ["water"] = "grass-1",\r
13   ["deepwater"] = "grass-1",\r
14   ["water-green"] = "grass-1",\r
15   ["deepwater-green"] = "grass-1"\r
16 }\r
17 \r
18 script.on_configuration_changed(function(data)\r
19   if global.bombs ~= nil then\r
20     for k,v in pairs(global.bombs) do\r
21       if v[1].valid and v[5] == nil then\r
22         v[5] = v[1].surface\r
23       end\r
24     end\r
25 \r
26     if global.ticks == nil then\r
27       global.ticks = 0\r
28     end\r
29   end\r
30 end)\r
31 \r
32 script.on_load(function(event)\r
33   if global.bombs ~= nil then\r
34     bombs = global.bombs\r
35     script.on_event(defines.events.on_tick, tickBombs)\r
36   end\r
37 end)\r
38 \r
39 function tickBombs()\r
40   if global.ticks > 0 then global.ticks = global.ticks - 1 else global.ticks = 10, executeTicks() end\r
41 end\r
42 \r
43 function executeTicks()\r
44   local x,y\r
45   local distX,distY\r
46   local energy\r
47 \r
48   for k,v in pairs(bombs) do\r
49     if v[1].valid and v[2] == 0 then\r
50       energy = v[1].energy\r
51 \r
52       if energy > 49000000 then\r
53         x = v[1].position.x\r
54         y = v[1].position.y\r
55 \r
56         for xx = x - 5.5,x + 5.5,1.5 do\r
57           for yy = y - 5.5,y + 5.5,1.5 do\r
58             distX = math.abs(x - xx)\r
59             distY = math.abs(y - yy)\r
60 \r
61             if math.floor(math.sqrt((distX * distX) + (distY * distY))) <= 5 then\r
62               v[1].surface.create_entity({name = "medium-explosion", position = {x = xx, y = yy}})\r
63             end\r
64           end\r
65         end\r
66 \r
67         v[5].create_entity({name = "water-bomb-detonation", position = v[1].position, target = v[1], speed = 1})\r
68         v[4] = v[1].position\r
69         v[1].destroy()\r
70         v[2] = 1\r
71         v[3] = game.tick\r
72 \r
73                 --[[changed by someone1337: use explosionRadius instead of hardcoded radius]]\r
74         createWater(x, y, explosionRadius, v[5])\r
75         throwDirt(x, y, explosionRadius, v[5])\r
76 -- no smoke for now\r
77  --     else\r
78  --       if energy > 40000000 then\r
79  --         v[5].create_entity({name = "smoke", position = v[1].position})\r
80  --         v[5].create_entity({name = "smoke", position = {x = v[1].position.x, y = v[1].position.y - 0.2}})\r
81  --       elseif energy > 30000000 then\r
82  --         v[5].create_entity({name = "smoke", position = v[1].position})\r
83  --       end\r
84       end\r
85     else\r
86       if v[2] == 1 then\r
87         if game.tick - v[3] > 90 then\r
88                   for a = 1,explosionRadius*2 do\r
89             createRandomStone(v[4], v[5])\r
90             createRandomStone(v[4], v[5])\r
91             createRandomStone(v[4], v[5])\r
92             createRandomStone(v[4], v[5])\r
93                   end\r
94           v[2] = 0\r
95         elseif game.tick - v[3] > 80 then\r
96                   for a = 1,explosionRadius*2 do\r
97             createRandomStone(v[4], v[5])\r
98             createRandomStone(v[4], v[5])\r
99             createRandomStone(v[4], v[5])\r
100             createRandomStone(v[4], v[5])\r
101                   end\r
102         elseif game.tick - v[3] > 70 then\r
103                   for a = 1,explosionRadius*2 do\r
104             createRandomStone(v[4], v[5])\r
105             createRandomStone(v[4], v[5])\r
106                   end\r
107         elseif game.tick - v[3] > 60 then\r
108                   for a = 1,explosionRadius*2 do\r
109             createRandomStone(v[4], v[5])\r
110             createRandomStone(v[4], v[5])\r
111             createRandomStone(v[4], v[5])\r
112                   end\r
113         end\r
114       else\r
115         table.remove(bombs, k)\r
116         if #global.bombs == 0 then\r
117           bombs = nil\r
118           global.bombs = nil\r
119           script.on_event(defines.events.on_tick, nil)\r
120         end\r
121       end\r
122     end\r
123   end\r
124 end\r
125 \r
126 function createWater(x, y, size, surface)\r
127   local players = surface.find_entities_filtered({area = {{x - size - 1, y - size - 1}, {x + size + 1, y + size + 1}}, type="player"})\r
128   -- Setting tiles to water where players are standing deletes the player and sets them to god mode.\r
129   if #players ~= 0 then\r
130     return\r
131   end\r
132 \r
133   local waterTiles = {}\r
134   x = math.floor(x)\r
135   y = math.floor(y)\r
136 \r
137   for wx = x - size, x + size, 1 do\r
138     for wy = y - size, y + size, 1 do\r
139       table.insert(waterTiles, {name="water", position={wx, wy}})\r
140     end\r
141   end\r
142 \r
143   surface.set_tiles(waterTiles)\r
144 \r
145   -- [[ changed by someone1337: deep water at the place of the bomb itself]]\r
146   waterTiles = {}\r
147   table.insert(waterTiles, {name="deepwater", position={x, y}})\r
148   surface.set_tiles(waterTiles)\r
149 end\r
150 \r
151 function throwDirt(x, y, size, surface)\r
152   local dirtTiles = {}\r
153   local tileName\r
154   local floor = math.floor\r
155   local distX,distY\r
156 \r
157   if displaceDirt == true then\r
158     x = floor(x)\r
159     y = floor(y)\r
160 \r
161     for xx = x - (size + 1), x + (size + 1), 1 do\r
162       for yy = y - (size + 1), y + (size + 1), 1 do\r
163         distX = math.abs(x - xx)\r
164         distY = math.abs(y - yy)\r
165 \r
166         if floor(math.sqrt((distX * distX) + (distY * distY))) >= 2 then\r
167           table.insert(dirtTiles, {name = "grass-1", position = {xx, yy}})\r
168         end\r
169       end\r
170     end\r
171 \r
172     if #dirtTiles ~= 0 then\r
173       surface.set_tiles(dirtTiles)\r
174     end\r
175   end\r
176 end\r
177 \r
178 function createRandomStone(position, surface)\r
179   local x,y\r
180   local tileName\r
181   local floor = math.floor\r
182   local random = math.random\r
183 \r
184   if throwRocks == true then\r
185     x = position.x\r
186     y = position.y\r
187 \r
188     if random() > 0.5 then\r
189       x = x - floor(random(2, maximumRockThrowDistance))\r
190     else\r
191       x = x + floor(random(2, maximumRockThrowDistance))\r
192     end\r
193 \r
194     if random() < 0.5 then\r
195       y = y - floor(random(2, maximumRockThrowDistance))\r
196     else\r
197       y = y + floor(random(2, maximumRockThrowDistance))\r
198     end\r
199 \r
200     tileName = surface.get_tile(floor(x), floor(y)).name\r
201 \r
202     if replaceableTiles[tileName] then\r
203       if throwRocksIntoWater == true then\r
204         surface.set_tiles({{name=replaceableTiles[tileName], position={floor(x), floor(y)}}})\r
205       end\r
206     else\r
207           if floor(random(1, 4)) > 2 then\r
208         surface.create_entity({name = "stone", position = {x, y}}).amount = floor(random(13, 27))\r
209         surface.create_entity({name = "explosion", position = {x, y}})\r
210 --        surface.create_entity({name = "smoke", position = {x, y}})\r
211       end\r
212     end\r
213   end\r
214 end\r
215 \r
216 script.on_event(defines.events.on_built_entity, function(event)\r
217   local newBomb\r
218   local bombEntity\r
219   local player = game.players[event.player_index]\r
220 \r
221   if event.created_entity.name == "water-bomb-area" then\r
222     bombEntity = player.surface.create_entity({name = "water-bomb", position = event.created_entity.position, force = event.created_entity.force})\r
223     event.created_entity.destroy()\r
224 \r
225     if global.bombs == nil then\r
226       global.bombs = {}\r
227       bombs = global.bombs\r
228       script.on_event(defines.events.on_tick, tickBombs)\r
229       if global.ticks == nil then\r
230         global.ticks = 0\r
231       end\r
232     end\r
233 \r
234     newBomb = {}\r
235     newBomb[1] = bombEntity        -- Bomb entity\r
236     newBomb[2] = 0            -- Bomb state (charging:0, detonated:1)\r
237     newBomb[3] = 0            -- Tick detonation occurred\r
238     newBomb[5] = bombEntity.surface\r
239 \r
240     table.insert(bombs, newBomb)\r
241   end\r
242 end)\r
243 \r
244 \r
245 function setTilesAndUpdateChunks(tiles, chunks, player)\r
246   player.surface.set_tiles(tiles)\r
247 \r
248   -- Creates a stone entity in each chunk effected by the flood fill triggering a minimap update and then destroys it\r
249   if chunks ~= nil then\r
250     local force = player.force\r
251     for x in pairs(chunks) do\r
252       for y in pairs(chunks[x]) do\r
253         player.surface.create_entity({name = "stone", position = {x * 32, y * 32}, force = force}).destroy()\r
254       end\r
255     end\r
256   end\r
257 end\r
258 \r
259 \r
260 function modifyReplaceableTile(sourceTile, replaceTile)\r
261   if not replaceableTiles[sourceTile] or replaceableTiles[sourceTile] ~= replaceTile then\r
262     replaceableTiles[sourceTile] = replaceTile\r
263   end\r
264 end\r