1 -- mods/default/mapgen.lua
4 -- Aliases for map generator outputs
7 minetest.register_alias("mapgen_stone", "default:stone")
8 minetest.register_alias("mapgen_tree", "default:tree")
9 minetest.register_alias("mapgen_leaves", "default:leaves")
10 minetest.register_alias("mapgen_jungletree", "default:jungletree")
11 minetest.register_alias("mapgen_jungleleaves", "default:jungleleaves")
12 minetest.register_alias("mapgen_apple", "default:apple")
13 minetest.register_alias("mapgen_water_source", "default:water_source")
14 minetest.register_alias("mapgen_dirt", "default:dirt")
15 minetest.register_alias("mapgen_sand", "default:sand")
16 minetest.register_alias("mapgen_gravel", "default:gravel")
17 minetest.register_alias("mapgen_clay", "default:clay")
18 minetest.register_alias("mapgen_lava_source", "default:lava_source")
19 minetest.register_alias("mapgen_cobble", "default:cobble")
20 minetest.register_alias("mapgen_mossycobble", "default:mossycobble")
21 minetest.register_alias("mapgen_dirt_with_grass", "default:dirt_with_grass")
22 minetest.register_alias("mapgen_junglegrass", "default:junglegrass")
23 minetest.register_alias("mapgen_stone_with_coal", "default:stone_with_coal")
24 minetest.register_alias("mapgen_stone_with_iron", "default:stone_with_iron")
25 minetest.register_alias("mapgen_mese", "default:mese")
26 minetest.register_alias("mapgen_desert_sand", "default:desert_sand")
27 minetest.register_alias("mapgen_desert_stone", "default:desert_stone")
28 minetest.register_alias("mapgen_stair_cobble", "stairs:stair_cobble")
34 function default.register_ores()
35 minetest.register_ore({
37 ore = "default:stone_with_coal",
38 wherein = "default:stone",
39 clust_scarcity = 8*8*8,
46 minetest.register_ore({
48 ore = "default:stone_with_coal",
49 wherein = "default:stone",
50 clust_scarcity = 24*24*24,
58 minetest.register_ore({
60 ore = "default:stone_with_iron",
61 wherein = "default:stone",
62 clust_scarcity = 12*12*12,
69 minetest.register_ore({
71 ore = "default:stone_with_iron",
72 wherein = "default:stone",
73 clust_scarcity = 9*9*9,
80 minetest.register_ore({
82 ore = "default:stone_with_iron",
83 wherein = "default:stone",
84 clust_scarcity = 7*7*7,
92 minetest.register_ore({
94 ore = "default:stone_with_iron",
95 wherein = "default:stone",
96 clust_scarcity = 24*24*24,
104 minetest.register_ore({
105 ore_type = "scatter",
106 ore = "default:stone_with_mese",
107 wherein = "default:stone",
108 clust_scarcity = 18*18*18,
116 minetest.register_ore({
117 ore_type = "scatter",
118 ore = "default:stone_with_mese",
119 wherein = "default:stone",
120 clust_scarcity = 14*14*14,
128 minetest.register_ore({
129 ore_type = "scatter",
130 ore = "default:mese",
131 wherein = "default:stone",
132 clust_scarcity = 36*36*36,
140 minetest.register_ore({
141 ore_type = "scatter",
142 ore = "default:stone_with_gold",
143 wherein = "default:stone",
144 clust_scarcity = 15*15*15,
152 minetest.register_ore({
153 ore_type = "scatter",
154 ore = "default:stone_with_gold",
155 wherein = "default:stone",
156 clust_scarcity = 13*13*13,
164 minetest.register_ore({
165 ore_type = "scatter",
166 ore = "default:stone_with_diamond",
167 wherein = "default:stone",
168 clust_scarcity = 17*17*17,
176 minetest.register_ore({
177 ore_type = "scatter",
178 ore = "default:stone_with_diamond",
179 wherein = "default:stone",
180 clust_scarcity = 15*15*15,
188 minetest.register_ore({
189 ore_type = "scatter",
190 ore = "default:stone_with_copper",
191 wherein = "default:stone",
192 clust_scarcity = 12*12*12,
199 minetest.register_ore({
200 ore_type = "scatter",
201 ore = "default:stone_with_copper",
202 wherein = "default:stone",
203 clust_scarcity = 9*9*9,
211 minetest.register_ore({
213 ore = "default:clay",
214 wherein = {"default:sand"},
215 clust_scarcity = 24*24*24,
219 noise_threshhold = 0,
223 spread={x=5, y=5, z=5},
232 function default.generate_ore(name, wherein, minp, maxp, seed, chunks_per_volume, chunk_size, ore_per_chunk, height_min, height_max)
233 minetest.log('action', "WARNING: default.generate_ore is deprecated")
235 if maxp.y < height_min or minp.y > height_max then
238 local y_min = math.max(minp.y, height_min)
239 local y_max = math.min(maxp.y, height_max)
240 if chunk_size >= y_max - y_min + 1 then
243 local volume = (maxp.x-minp.x+1)*(y_max-y_min+1)*(maxp.z-minp.z+1)
244 local pr = PseudoRandom(seed)
245 local num_chunks = math.floor(chunks_per_volume * volume)
246 local inverse_chance = math.floor(chunk_size*chunk_size*chunk_size / ore_per_chunk)
247 --print("generate_ore num_chunks: "..dump(num_chunks))
248 for i=1,num_chunks do
249 local y0 = pr:next(y_min, y_max-chunk_size+1)
250 if y0 >= height_min and y0 <= height_max then
251 local x0 = pr:next(minp.x, maxp.x-chunk_size+1)
252 local z0 = pr:next(minp.z, maxp.z-chunk_size+1)
253 local p0 = {x=x0, y=y0, z=z0}
254 for x1=0,chunk_size-1 do
255 for y1=0,chunk_size-1 do
256 for z1=0,chunk_size-1 do
257 if pr:next(1,inverse_chance) == 1 then
261 local p2 = {x=x2, y=y2, z=z2}
262 if minetest.get_node(p2).name == wherein then
263 minetest.set_node(p2, {name=name})
271 --print("generate_ore done")
275 -- Mgv6 papyrus, cactus, long grasses
278 function default.mgv6_ongen(minp, maxp, seed)
280 function default.make_papyrus(pos, size)
282 local p = {x=pos.x, y=pos.y+y, z=pos.z}
283 local nn = minetest.get_node(p).name
284 if minetest.registered_nodes[nn] and
285 minetest.registered_nodes[nn].buildable_to then
286 minetest.set_node(p, {name="default:papyrus"})
293 function default.make_cactus(pos, size)
295 local p = {x=pos.x, y=pos.y+y, z=pos.z}
296 local nn = minetest.get_node(p).name
297 if minetest.registered_nodes[nn] and
298 minetest.registered_nodes[nn].buildable_to then
299 minetest.set_node(p, {name="default:cactus"})
306 if maxp.y >= 2 and minp.y <= 0 then
308 local perlin1 = minetest.get_perlin(354, 3, 0.7, 100)
309 -- Assume X and Z lengths are equal
311 local divs = (maxp.x-minp.x)/divlen+1;
314 local x0 = minp.x + math.floor((divx+0)*divlen)
315 local z0 = minp.z + math.floor((divz+0)*divlen)
316 local x1 = minp.x + math.floor((divx+1)*divlen)
317 local z1 = minp.z + math.floor((divz+1)*divlen)
318 -- Determine papyrus amount from perlin noise
319 local papyrus_amount = math.floor(perlin1:get2d({x=x0, y=z0}) * 45 - 20)
320 -- Find random positions for papyrus based on this random
321 local pr = PseudoRandom(seed+1)
322 for i=0,papyrus_amount do
323 local x = pr:next(x0, x1)
324 local z = pr:next(z0, z1)
325 if minetest.get_node({x=x,y=1,z=z}).name == "default:dirt_with_grass" and
326 minetest.find_node_near({x=x,y=1,z=z}, 1, "default:water_source") then
327 default.make_papyrus({x=x,y=2,z=z}, pr:next(2, 4))
333 local perlin1 = minetest.get_perlin(230, 3, 0.6, 100)
334 -- Assume X and Z lengths are equal
336 local divs = (maxp.x-minp.x)/divlen+1;
339 local x0 = minp.x + math.floor((divx+0)*divlen)
340 local z0 = minp.z + math.floor((divz+0)*divlen)
341 local x1 = minp.x + math.floor((divx+1)*divlen)
342 local z1 = minp.z + math.floor((divz+1)*divlen)
343 -- Determine cactus amount from perlin noise
344 local cactus_amount = math.floor(perlin1:get2d({x=x0, y=z0}) * 6 - 3)
345 -- Find random positions for cactus based on this random
346 local pr = PseudoRandom(seed+1)
347 for i=0,cactus_amount do
348 local x = pr:next(x0, x1)
349 local z = pr:next(z0, z1)
350 -- Find ground level (0...15)
353 if minetest.get_node({x=x,y=y,z=z}).name ~= "air" then
358 -- If desert sand, make cactus
359 if ground_y and minetest.get_node({x=x,y=ground_y,z=z}).name == "default:desert_sand" then
360 default.make_cactus({x=x,y=ground_y+1,z=z}, pr:next(3, 4))
366 local perlin1 = minetest.get_perlin(329, 3, 0.6, 100)
367 -- Assume X and Z lengths are equal
369 local divs = (maxp.x-minp.x)/divlen+1;
372 local x0 = minp.x + math.floor((divx+0)*divlen)
373 local z0 = minp.z + math.floor((divz+0)*divlen)
374 local x1 = minp.x + math.floor((divx+1)*divlen)
375 local z1 = minp.z + math.floor((divz+1)*divlen)
376 -- Determine grass amount from perlin noise
377 local grass_amount = math.floor(perlin1:get2d({x=x0, y=z0}) ^ 3 * 9)
378 -- Find random positions for grass based on this random
379 local pr = PseudoRandom(seed+1)
380 for i=0,grass_amount do
381 local x = pr:next(x0, x1)
382 local z = pr:next(z0, z1)
383 -- Find ground level (0...15)
386 if minetest.get_node({x=x,y=y,z=z}).name ~= "air" then
393 local p = {x=x,y=ground_y+1,z=z}
394 local nn = minetest.get_node(p).name
395 -- Check if the node can be replaced
396 if minetest.registered_nodes[nn] and
397 minetest.registered_nodes[nn].buildable_to then
398 nn = minetest.get_node({x=x,y=ground_y,z=z}).name
399 -- If desert sand, add dry shrub
400 if nn == "default:desert_sand" then
401 minetest.set_node(p,{name="default:dry_shrub"})
403 -- If dirt with grass, add grass
404 elseif nn == "default:dirt_with_grass" then
405 minetest.set_node(p,{name="default:grass_"..pr:next(1, 5)})
418 -- Generate nyan cats in all mapgens
421 -- facedir: 0/1/2/3 (head node facedir value)
422 -- length: length of rainbow tail
423 function default.make_nyancat(pos, facedir, length)
424 local tailvec = {x=0, y=0, z=0}
427 elseif facedir == 1 then
429 elseif facedir == 2 then
431 elseif facedir == 3 then
434 --print("default.make_nyancat(): Invalid facedir: "+dump(facedir))
438 local p = {x=pos.x, y=pos.y, z=pos.z}
439 minetest.set_node(p, {name="default:nyancat", param2=facedir})
441 p.x = p.x + tailvec.x
442 p.z = p.z + tailvec.z
443 minetest.set_node(p, {name="default:nyancat_rainbow", param2=facedir})
448 function default.generate_nyancats(minp, maxp, seed)
449 local height_min = -31000
450 local height_max = -32
451 if maxp.y < height_min or minp.y > height_max then
454 local y_min = math.max(minp.y, height_min)
455 local y_max = math.min(maxp.y, height_max)
456 local volume = (maxp.x-minp.x+1)*(y_max-y_min+1)*(maxp.z-minp.z+1)
457 local pr = PseudoRandom(seed + 9324342)
458 local max_num_nyancats = math.floor(volume / (16*16*16))
459 for i=1,max_num_nyancats do
460 if pr:next(0, 1000) == 0 then
461 local x0 = pr:next(minp.x, maxp.x)
462 local y0 = pr:next(minp.y, maxp.y)
463 local z0 = pr:next(minp.z, maxp.z)
464 local p0 = {x=x0, y=y0, z=z0}
465 default.make_nyancat(p0, pr:next(0,3), pr:next(3,15))
471 minetest.register_on_generated(default.generate_nyancats)
477 function default.register_biomes()
478 minetest.clear_registered_biomes()
480 minetest.register_biome({
482 node_top = "default:dirt_with_grass",
483 node_shore_top = "default:sand",
485 node_filler = "default:dirt",
486 node_shore_filler = "default:sand",
489 node_underwater = "default:sand",
491 --node_water_top = "",
492 --depth_water_top = ,
502 -- Register decorations
507 minetest.register_decoration({
508 deco_type = "simple",
509 place_on = {"default:dirt_with_grass"},
514 spread = {x=100, y=100, z=100},
519 biomes = {"grassland"},
522 decoration = "flowers:rose",
525 minetest.register_decoration({
526 deco_type = "simple",
527 place_on = {"default:dirt_with_grass"},
532 spread = {x=100, y=100, z=100},
537 biomes = {"grassland"},
540 decoration = "flowers:tulip",
543 minetest.register_decoration({
544 deco_type = "simple",
545 place_on = {"default:dirt_with_grass"},
550 spread = {x=100, y=100, z=100},
555 biomes = {"grassland"},
558 decoration = "flowers:dandelion_yellow",
561 minetest.register_decoration({
562 deco_type = "simple",
563 place_on = {"default:dirt_with_grass"},
568 spread = {x=100, y=100, z=100},
573 biomes = {"grassland"},
576 decoration = "flowers:geranium",
579 minetest.register_decoration({
580 deco_type = "simple",
581 place_on = {"default:dirt_with_grass"},
586 spread = {x=100, y=100, z=100},
591 biomes = {"grassland"},
594 decoration = "flowers:viola",
597 minetest.register_decoration({
598 deco_type = "simple",
599 place_on = {"default:dirt_with_grass"},
604 spread = {x=100, y=100, z=100},
609 biomes = {"grassland"},
612 decoration = "flowers:dandelion_white",
617 minetest.register_decoration({
618 deco_type = "simple",
619 place_on = {"default:dirt_with_grass"},
624 spread = {x=100, y=100, z=100},
629 biomes = {"grassland"},
632 decoration = "default:grass_1",
635 minetest.register_decoration({
636 deco_type = "simple",
637 place_on = {"default:dirt_with_grass"},
642 spread = {x=100, y=100, z=100},
647 biomes = {"grassland"},
650 decoration = "default:grass_2",
653 minetest.register_decoration({
654 deco_type = "simple",
655 place_on = {"default:dirt_with_grass"},
660 spread = {x=100, y=100, z=100},
665 biomes = {"grassland"},
668 decoration = "default:grass_3",
671 minetest.register_decoration({
672 deco_type = "simple",
673 place_on = {"default:dirt_with_grass"},
678 spread = {x=100, y=100, z=100},
683 biomes = {"grassland"},
686 decoration = "default:grass_4",
689 minetest.register_decoration({
690 deco_type = "simple",
691 place_on = {"default:dirt_with_grass"},
696 spread = {x=100, y=100, z=100},
701 biomes = {"grassland"},
704 decoration = "default:grass_5",
712 function default.register_blobs()
713 minetest.register_ore({
715 ore = "default:sand",
716 wherein = {"default:stone"},
717 clust_scarcity = 24*24*24,
721 noise_threshhold = 0,
725 spread={x=5, y=5, z=5},
732 minetest.register_ore({
734 ore = "default:dirt",
735 wherein = {"default:stone"},
736 clust_scarcity = 24*24*24,
740 noise_threshhold = 0,
744 spread={x=5, y=5, z=5},
751 minetest.register_ore({
753 ore = "default:gravel",
754 wherein = {"default:stone"},
755 clust_scarcity = 24*24*24,
759 noise_threshhold = 0,
763 spread={x=5, y=5, z=5},
772 -- Detect mapgen and select suitable biome code
775 local mg_params = minetest.get_mapgen_params()
776 if mg_params.mgname == "v5" then
777 default.register_biomes()
778 default.register_blobs()
779 default.register_ores()
780 elseif mg_params.mgname == "v6" then
781 minetest.register_on_generated(default.mgv6_ongen)
782 default.register_ores()
783 elseif mg_params.mgname == "v7" then
784 default.register_biomes()
785 default.register_blobs()
786 default.register_ores()