]> git.lizzy.rs Git - elidragon.git/blob - skyblock.lua
Removed some ugly stuff, added auto show hud
[elidragon.git] / skyblock.lua
1 elidragon.skyblock = {} 
2
3 --helper functions
4
5 -- http://rosettacode.org/wiki/Spiral_matrix#Lua
6 av, sn = math.abs, function(s) return s~=0 and s/av(s) or 0 end
7 local function sindex(y, x)
8         if y == -x and y >= x then return (2*y+1)^2 end
9         local l = math.max(av(y), av(x))
10         return (2*l-1)^2+4*l+2*l*sn(x+y)+sn(y^2-x^2)*(l-(av(y)==l and sn(y)*x or sn(x)*y))
11 end
12 local function spiralt(side)
13         local ret, id, start, stop = {}, 0, math.floor((-side+1)/2), math.floor((side-1)/2)
14         for i = 1, side do
15                 for j = 1, side do
16                         local id = side^2 - sindex(stop - i + 1,start + j - 1)
17                         ret[id] = {x=i,z=j}
18                 end
19         end
20         return ret
21 end
22
23 local function ripairs(t)
24         local function ripairs_it(t,i)
25                 i=i-1
26                 local v=t[i]
27                 if v==nil then return v end
28                 return i,v
29         end
30         return ripairs_it, t, #t+1
31 end
32
33 -- start positions
34
35 function elidragon.skyblock.load_legacy_start_positions()
36         local file = io.open(minetest.get_worldpath() .. "/skyblock.start_positions", "r")
37         if file then
38                 local start_positions = {}
39                 while true do
40                         local x = file:read("*n")
41                         if x == nil then
42                                 break
43                         end
44                         local y = file:read("*n")
45                         local z = file:read("*n")
46                         table.insert(start_positions, {x = x, y = y, z = z})
47                 end
48                 file:close()
49                 return start_positions
50         end
51 end
52
53 function elidragon.skyblock.load_start_positions()
54         local file = io.open(minetest.get_worldpath() .. "/start_positions", "r")
55         if file then
56                 local start_positions = minetest.deserialize(file:read())
57                 file:close()
58                 return start_positions
59         end
60 end
61
62 function elidragon.skyblock.save_start_positions(start_positions)
63         local file = io.open(minetest.get_worldpath() .. "/start_positions", "w")
64         file:write(minetest.serialize(start_positions))
65         file:close()
66 end
67
68 function elidragon.skyblock.generate_start_positions()
69         local start_positions = {}
70         for _, v in ripairs(spiralt(1000)) do
71                 local pos = {x = v.x * 32, y = math.random(4 - 8, 4 + 8), z = v.z * 32}
72                 table.insert(start_positions, pos)
73         end
74         return start_positions
75 end
76
77 elidragon.skyblock.start_positions = elidragon.skyblock.load_start_positions() 
78
79 if not elidragon.skyblock.start_positions then
80         elidragon.skyblock.start_positions = elidragon.skyblock.load_legacy_start_positions() or elidragon.skyblock.generate_start_positions()
81         elidragon.skyblock.save_start_positions(elidragon.skyblock.start_positions)
82 end
83
84 function elidragon.skyblock.load_legacy_last_start_id()
85         local file = io.open(minetest.get_worldpath() .. "/skyblock.last_start_id", "r")
86         if file then
87                 local last_start_id = tonumber(file:read())
88                 file:close()
89                 return last_start_id
90         end
91 end
92
93 elidragon.savedata.last_start_id = elidragon.savedata.last_start_id or elidragon.skyblock.load_legacy_last_start_id() or 0
94
95 -- spawns
96
97 function elidragon.skyblock.get_spawn(name)
98         return elidragon.savedata.spawns[name]
99 end
100
101 function elidragon.skyblock.set_spawn(name, pos)
102         elidragon.savedata.spawns[name] = pos
103 end
104
105 function elidragon.skyblock.spawn_player(player)
106         if not player then return end
107         local name = player:get_player_name()
108         local spawn = elidragon.skyblock.get_spawn(name) or elidragon.skyblock.new_spawn(name)
109         player:set_pos({x = spawn.x + 2, y = spawn.y + 2, z = spawn.z + 2})
110 end
111
112 function elidragon.skyblock.new_spawn(name)
113         local spawn
114         repeat
115                 elidragon.savedata.last_start_id = elidragon.savedata.last_start_id + 1
116                 spawn = elidragon.skyblock.start_positions[elidragon.savedata.last_start_id] 
117         until not minetest.is_protected(spawn, name)
118         elidragon.skyblock.set_spawn(name, spawn)       
119         local file = io.open(minetest.get_modpath("elidragon") .. "/schems/island.we", "r")
120         local schem = file:read()
121         file:close()
122         worldedit.deserialize(vector.add(spawn, {x = -3, y = -4, z = -3}), schem) 
123         return spawn
124 end
125
126 function elidragon.skyblock.load_legacy_spawns()
127     local file = io.open(minetest.get_worldpath() .. "/skyblock.spawn", "r")
128     if file then
129                 local spawns = {}
130         while true do
131             local x = file:read("*n")
132             if x == nil then
133                 break
134             end
135             local y = file:read("*n")
136             local z = file:read("*n")
137             local name = file:read("*l")
138             spawns[name:sub(2)] = {x = x, y = y, z = z}
139         end
140         file:close()
141         return spawns
142         end
143 end
144
145 elidragon.savedata.spawns = elidragon.savedata.spawns or elidragon.skyblock.load_legacy_spawns() or {}
146
147
148 -- level
149 --[[
150 minetest.register_chatcommand("level", {
151         description = "Get/set the current level of a player",
152         params = "<player> [<level>]",
153         func = function(name, param)
154                 local target = param:split(" ")[1]
155                 local level = tonumber(param:split(" ")[2])
156                 if not level then
157                         minetest.chat_send_player(name, target .. " is on level " .. elidragon.skyblock.get_level(target))
158                 elseif minetest.check_player_privs(name, {server = true}) and elidragon.skyblock.set_level(target, level) then
159                         minetest.chat_send_player(name, target .. " has been set to level " .. level)
160                 else
161                         minetest.chat_send_player(name, "Cannot change " .. target .. " to level " .. level)
162                 end
163         end,
164 })
165 ]]--
166
167 -- node
168
169 minetest.register_node("elidragon:skyblock", {
170         description = "Skyblock",
171         tiles = {"elidragon_quest.png"},
172         paramtype = "light",
173         light_source = 14,
174         groups = {crumbly=2, cracky=2},
175 })
176
177 minetest.register_alias("skyblock:quest", "elidragon:skyblock")
178
179 -- mapgen
180
181 minetest.register_on_mapgen_init(function(mgparams)
182         minetest.set_mapgen_params({mgname = "singlenode", water_level = -32000})
183 end)
184
185 -- respawn
186
187 minetest.register_on_respawnplayer(function(player)
188         elidragon.skyblock.spawn_player(player)
189         return true
190 end)
191
192 -- remove legacy cloud layer
193
194 minetest.register_lbm({
195         nodenames = {"default:cloud"},
196         name = "elidragon:remove_cloud_layer",
197         action = function(pos)
198                 if pos.y == -10 then
199                         minetest.set_node(pos, { name = "air"})
200                 end
201         end
202 })
203
204 -- remove inventory from quest block
205
206 minetest.register_lbm({
207         nodenames = {"elidragon:skyblock", "skyblock:quest"},
208         name = "elidragon:remove_inventory_from_quest_block",
209         action = function(pos)
210                 minetest.get_meta(pos):set_string("formspec", "")
211                 minetest.get_meta(pos):set_string("infotext", "")
212         end
213 })
214
215 -- ores
216
217 minetest.after(0, function()
218         default.cool_lava = function(pos, oldnode)
219                 local node
220                 if oldnode.name == "default:lava_source" then
221                         node = "default:obsidian"
222                 elseif math.random() < 0.001 then
223                         node = "moreores:mineral_mithril"
224                 elseif math.random() < 0.003 then
225                         node = "default:stone_with_diamond"
226                 elseif math.random() < 0.005 then
227                         node = "default:stone_with_mese"
228                 elseif math.random() < 0.01 then
229                         node = "default:stone_with_gold"
230                 elseif math.random() < 0.01 then
231                         node = "technic:mineral_chromium"
232                 elseif math.random() < 0.01 then
233                         node = "technic:mineral_zinc"
234                 elseif math.random() < 0.012 then
235                         node = "technic:mineral_uranium"
236                 elseif math.random() < 0.015 then
237                         node = "default:stone_with_tin"
238                 elseif math.random() < 0.02 then
239                         node = "default:stone_with_copper"
240                 elseif math.random() < 0.025 then
241                         node = "technic:mineral_sulfur"
242                 elseif math.random() < 0.033 then
243                         node = "default:stone_with_iron"
244                 elseif math.random() < 0.04 then
245                         node = "moreores:mineral_silver"
246                 elseif math.random() < 0.045 then
247                         node = "technic:mineral_lead"
248                 elseif math.random() < 0.05 then
249                         node = "default:stone_with_coal"
250                 else
251                         node = "default:stone"
252                 end
253                 minetest.set_node(pos, {name = node})
254                 minetest.sound_play("default_cool_lava", {pos = pos, max_hear_distance = 16, gain = 0.25}, true)
255         end
256 end)
257
258 -- saplings
259
260 minetest.after(0, function()
261         minetest.register_alias("default:pine_leaves", "default:pine_needles")
262         minetest.register_alias("default:pine_bush_leaves", "default:pine_bush_needles")
263         local trees = {"default:", "default:jungle", "default:pine_", "default:acacia_", "default:aspen_", "default:bush_", "default:blueberry_bush_", "default:acacia_bush_", "default:pine_bush_", "moretrees:apple_tree_", "moretrees:beech_", "moretrees:cedar_", "moretrees:date_palm_", "moretrees:fir_", "moretrees:oak_", "moretrees:palm_", "moretrees:poplar_", "moretrees:sequoia_", "moretrees:spruce_", "moretrees:willow_", }
264         for _, tree in pairs(trees) do
265                 local items = {}
266                 items[#items + 1] = {
267                         items = {tree .. "sapling"},
268                         rarity = 20,
269                 }
270                 for _, stree in pairs(trees) do
271                         if stree ~= tree then
272                                 items[#items + 1] = {
273                                         items = {stree .. "sapling"},
274                                         rarity = 1000,
275                                 }
276                         end
277                 end
278                 items[#items + 1] = {
279                         items = {tree .. "leaves"},
280                 }
281                 minetest.registered_nodes[tree .. "leaves"].drop = {max_items = 1, items = items}
282         end
283 end)
284
285 -- flowers
286
287 minetest.register_abm({
288         nodenames = {"default:dirt_with_grass"},
289         interval = 300,
290         chance = 100,
291         action = function(pos, node)
292                 pos.y = pos.y + 1
293                 local light = minetest.get_node_light(pos) or 0
294                 if minetest.get_node(pos).name == "air" and light > 12 and not minetest.find_node_near(pos, 2, {"group:flora"}) then
295                         local flowers = {"default:junglegrass", "default:grass_1", "flowers:dandelion_white", "flowers:dandelion_yellow", "flowers:geranium", "flowers:rose", "flowers:tulip", "flowers:tulip_black", "flowers:viola", "flowers:chrysanthemum_green"}
296                         minetest.set_node(pos, {name = flowers[math.random(#flowers)]})
297                 end
298         end
299 })
300
301 -- recipes
302
303 minetest.register_craft({
304         output = "default:desert_sand",
305         recipe = {
306                 {"default:sand"},
307                 {"default:gravel"},
308         }
309 })
310
311 minetest.register_craft({
312         output = "default:desert_stone",
313         recipe = {
314                 {"default:desert_sand", "default:desert_sand", "default:desert_sand"},
315                 {"default:desert_sand", "default:desert_sand", "default:desert_sand"},
316                 {"default:desert_sand", "default:desert_sand", "default:desert_sand"},
317         }
318 })
319
320 minetest.register_craft({
321         output = "default:sand 4",
322         recipe = {
323                 {"default:obsidian_shard"},
324         }
325 })
326
327 minetest.register_craft({
328         output = "default:gravel 2",
329         recipe = {
330                 {"default:cobble"},
331         }
332 })
333
334 minetest.register_craft({
335         output = "default:dirt 2",
336         recipe = {
337                 {"default:gravel"},
338         }
339 })
340
341 minetest.register_craft({
342         output = "default:clay_lump 4",
343         recipe = {
344                 {"default:dirt"},
345         }
346 })
347
348 minetest.register_craft({
349         output = "default:ice",
350         recipe = {
351                 {"bucket:bucket_water"},
352         }
353 })
354
355 minetest.register_craft({
356         output = "default:snowblock 4",
357         recipe = {
358                 {"default:ice"},
359         }
360 })
361
362 minetest.register_craft({
363         type = "cooking",
364         output = "default:lava_source",
365         recipe = "default:stone",
366 })
367
368 minetest.register_craft({
369         output = "default:silver_sand 9",
370         recipe = {
371                 {"default:sand", "default:sand", "default:sand"},
372                 {"default:sand", "moreores:silver_lump", "default:sand"},
373                 {"default:sand", "default:sand", "default:sand"},
374         }
375 })
376
377 -- commands
378
379 minetest.register_chatcommand("set_skyblock_spawn", {
380     param = "<player> <x> <y> <z>",
381     desc = "Change the skyblocks spawn of a player",
382     privs = {server = true},
383     func = function(admin, param)
384         local name = param:split(" ")[1]
385         local x = tonumber(param:split(" ")[2])
386         local y = tonumber(param:split(" ")[3])
387         local z = tonumber(param:split(" ")[4])
388         if name and x and y and z then
389             elidragon.skyblock.set_spawn(name, {x = x, y = y, z = z})
390         else
391             minetest.chat_send_player(admin, "Invalid usage.")
392         end
393     end
394 })
395
396 minetest.register_chatcommand("island", {
397         params = "",
398         description = "Teleport to your Island",
399         func = function(name, param)
400                 elidragon.skyblock.spawn_player(minetest.get_player_by_name(name))
401         end,
402 })