forked from MineClone5/MineClone5
Start adding new structures API
This commit is contained in:
parent
16116df4c6
commit
c6754fd39e
|
@ -71,7 +71,7 @@ Registers callback function to be called when current chunk generation is REALLY
|
||||||
For LVM it's the most frustrating function from this mod.
|
For LVM it's the most frustrating function from this mod.
|
||||||
It can't provide you access to mapgen objects. They are probably gone long ago.
|
It can't provide you access to mapgen objects. They are probably gone long ago.
|
||||||
Don't use it for accessing mapgen objects please.
|
Don't use it for accessing mapgen objects please.
|
||||||
To use VM you have to run `vm_context.vm = minetest.get_voxel_manip(vm_context.emin, vm_context.emax)`.
|
To use VM you have to run `vm_context.vm = mcl_mapgen.get_voxel_manip(vm_context.emin, vm_context.emax)`.
|
||||||
Set
|
Set
|
||||||
`callback_function`: callback function definition:
|
`callback_function`: callback function definition:
|
||||||
`function(minp, maxp, seed, vm_context)`:
|
`function(minp, maxp, seed, vm_context)`:
|
||||||
|
|
|
@ -29,9 +29,15 @@ local gateway_positions = {
|
||||||
local path_gateway_portal = minetest.get_modpath("mcl_structures").."/schematics/mcl_structures_end_gateway_portal.mts"
|
local path_gateway_portal = minetest.get_modpath("mcl_structures").."/schematics/mcl_structures_end_gateway_portal.mts"
|
||||||
|
|
||||||
local function spawn_gateway_portal(pos, dest_str)
|
local function spawn_gateway_portal(pos, dest_str)
|
||||||
return mcl_structures.place_schematic(vector.add(pos, vector.new(-1, -2, -1)), path_gateway_portal, "0", nil, true, nil, dest_str and function()
|
return mcl_structures.place_schematic({
|
||||||
minetest.get_meta(pos):set_string("mcl_portals:gateway_destination", dest_str)
|
pos = vector.add(pos, vector.new(-1, -2, -1)),
|
||||||
end)
|
schematic = path_gateway_portal,
|
||||||
|
rotation = "0",
|
||||||
|
force_placement = true,
|
||||||
|
after_place = dest_str and function()
|
||||||
|
minetest.get_meta(pos):set_string("mcl_portals:gateway_destination", dest_str)
|
||||||
|
end,
|
||||||
|
})
|
||||||
end
|
end
|
||||||
|
|
||||||
function mcl_portals.spawn_gateway_portal()
|
function mcl_portals.spawn_gateway_portal()
|
||||||
|
|
|
@ -10,25 +10,21 @@ local noisemap = PerlinNoiseMap({
|
||||||
local c_end_stone = minetest.get_content_id("mcl_end:end_stone")
|
local c_end_stone = minetest.get_content_id("mcl_end:end_stone")
|
||||||
local y_offset = -2
|
local y_offset = -2
|
||||||
|
|
||||||
mcl_mapgen.register_mapgen(function(minp, maxp)
|
mcl_mapgen.register_on_generated(function(vm_context)
|
||||||
|
local minp, maxp = vm_context.minp, vm_context.maxp
|
||||||
if maxp.y < (-27025 + y_offset) or minp.y > (-27000 + y_offset + 4) or maxp.x < -75 or minp.x > 75 or maxp.z < -75 or minp.z > 75 then
|
if maxp.y < (-27025 + y_offset) or minp.y > (-27000 + y_offset + 4) or maxp.x < -75 or minp.x > 75 or maxp.z < -75 or minp.z > 75 then
|
||||||
return
|
return
|
||||||
end
|
end
|
||||||
|
local data = vm_context.data
|
||||||
local vm, emin, emax = minetest.get_mapgen_object("voxelmanip")
|
local area = vm_context.area
|
||||||
local data = vm:get_data()
|
local write = false
|
||||||
local area = VoxelArea:new({MinEdge = emin, MaxEdge = emax})
|
|
||||||
|
|
||||||
for idx in area:iter(math.max(minp.x, -75), math.max(minp.y, -27025 + y_offset + 4), math.max(minp.z, -75), math.min(maxp.x, 75), math.min(maxp.y, -27000 + y_offset), math.min(maxp.z, 75)) do
|
for idx in area:iter(math.max(minp.x, -75), math.max(minp.y, -27025 + y_offset + 4), math.max(minp.z, -75), math.min(maxp.x, 75), math.min(maxp.y, -27000 + y_offset), math.min(maxp.z, 75)) do
|
||||||
local pos = area:position(idx)
|
local pos = area:position(idx)
|
||||||
local y = 27025 + pos.y - y_offset
|
local y = 27025 + pos.y - y_offset
|
||||||
if noisemap[pos.x + 75 + 1][y + 1][pos.z + 75 + 1] > (math.abs(1 - y / 25) ^ 2 + math.abs(pos.x / 75) ^ 2 + math.abs(pos.z / 75) ^ 2) then
|
if noisemap[pos.x + 75 + 1][y + 1][pos.z + 75 + 1] > (math.abs(1 - y / 25) ^ 2 + math.abs(pos.x / 75) ^ 2 + math.abs(pos.z / 75) ^ 2) then
|
||||||
data[idx] = c_end_stone
|
data[idx] = c_end_stone
|
||||||
|
write = true
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
vm_context.write = vm_context.write or write
|
||||||
vm:set_data(data)
|
|
||||||
vm:calc_lighting()
|
|
||||||
vm:update_liquids()
|
|
||||||
vm:write_to_map()
|
|
||||||
end)
|
end)
|
||||||
|
|
|
@ -11,37 +11,106 @@ local rotations = {
|
||||||
"270"
|
"270"
|
||||||
}
|
}
|
||||||
|
|
||||||
local function ecb_place(blockpos, action, calls_remaining, param)
|
local registered_structures = {}
|
||||||
if calls_remaining >= 1 then return end
|
|
||||||
minetest.place_schematic(param.pos, param.schematic, param.rotation, param.replacements, param.force_placement, param.flags)
|
function mcl_structures.register_structure(def)
|
||||||
if param.after_placement_callback and param.p1 and param.p2 then
|
local name = def.name
|
||||||
param.after_placement_callback(param.p1, param.p2, param.size, param.rotation, param.pr, param.callback_param)
|
if not name then
|
||||||
|
minetest.log('warning', 'Structure name is not passed for registering - ignoring')
|
||||||
|
return
|
||||||
end
|
end
|
||||||
|
if registered_structures[name] then
|
||||||
|
minetest.log('warning', 'Structure '..name..' is already registered - owerwriting')
|
||||||
|
end
|
||||||
|
registered_structures[name] = {
|
||||||
|
on_place = def.on_place,
|
||||||
|
decoration = def.decoration,
|
||||||
|
on_mapgen_prep = def.on_mapgen_prep,
|
||||||
|
on_generated = def.on_generated,
|
||||||
|
}
|
||||||
end
|
end
|
||||||
|
|
||||||
function mcl_structures.place_schematic(pos, schematic, rotation, replacements, force_placement, flags, after_placement_callback, pr, callback_param)
|
function mcl_structures.unregister_structure(name)
|
||||||
local s = loadstring(minetest.serialize_schematic(schematic, "lua", {lua_use_comments = false, lua_num_indent_spaces = 0}) .. " return schematic")()
|
if not registered_structures[name] then
|
||||||
if s and s.size then
|
minetest.log('warning','Structure '..name..' is not registered - skipping')
|
||||||
local x, z = s.size.x, s.size.z
|
return
|
||||||
if rotation then
|
|
||||||
if rotation == "random" and pr then
|
|
||||||
rotation = rotations[pr:next(1,#rotations)]
|
|
||||||
end
|
|
||||||
if rotation == "random" then
|
|
||||||
x = math.max(x, z)
|
|
||||||
z = x
|
|
||||||
elseif rotation == "90" or rotation == "270" then
|
|
||||||
x, z = z, x
|
|
||||||
end
|
|
||||||
end
|
|
||||||
local p1 = {x=pos.x , y=pos.y , z=pos.z }
|
|
||||||
local p2 = {x=pos.x+x-1, y=pos.y+s.size.y-1, z=pos.z+z-1}
|
|
||||||
minetest.log("verbose", "[mcl_structures] size=" ..minetest.pos_to_string(s.size) .. ", rotation=" .. tostring(rotation) .. ", emerge from "..minetest.pos_to_string(p1) .. " to " .. minetest.pos_to_string(p2))
|
|
||||||
local param = {pos=vector.new(pos), schematic=s, rotation=rotation, replacements=replacements, force_placement=force_placement, flags=flags, p1=p1, p2=p2, after_placement_callback = after_placement_callback, size=vector.new(s.size), pr=pr, callback_param=callback_param}
|
|
||||||
-- minetest.emerge_area(p1, p2, ecb_place, param)
|
|
||||||
-- TODO: Make it better
|
|
||||||
ecb_place(0, 0, 0, param)
|
|
||||||
end
|
end
|
||||||
|
registered_structures[name] = nil
|
||||||
|
end
|
||||||
|
|
||||||
|
local function ecb_place(blockpos, action, calls_remaining, param)
|
||||||
|
if calls_remaining >= 1 then return end
|
||||||
|
local pos = param.pos
|
||||||
|
local rotation = param.rotation
|
||||||
|
minetest.place_schematic(pos, param.schematic, rotation, param.replacements, param.force_placement, param.flags)
|
||||||
|
local after_place = param.after_place
|
||||||
|
if not after_place then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
after_place(pos, rotation, param.pr, param.param, param.size)
|
||||||
|
end
|
||||||
|
|
||||||
|
function mcl_structures.place_schematic(def)
|
||||||
|
local pos = def.pos
|
||||||
|
local schematic = def.schematic
|
||||||
|
local rotation = def.rotation
|
||||||
|
local pr = def.pr
|
||||||
|
if not pos then
|
||||||
|
minetest.log('warning', '[mcl_structures] No pos. specified to place schematic')
|
||||||
|
return
|
||||||
|
end
|
||||||
|
if not schematic then
|
||||||
|
minetest.log('warning', '[mcl_structures] No schematic specified to place at ' .. minetest.pos_to_string(pos))
|
||||||
|
return
|
||||||
|
end
|
||||||
|
if not rotation or rotation == 'random' then
|
||||||
|
if pr then
|
||||||
|
rotation = rotations[pr:next(1,#rotations)]
|
||||||
|
else
|
||||||
|
rotation = rotations[math.random(1,#rotations)]
|
||||||
|
end
|
||||||
|
end
|
||||||
|
if not def.emerge then
|
||||||
|
minetest.place_schematic(pos, schematic, rotation, def.replacements, def.force_placement, def.flags)
|
||||||
|
if not def.after_place then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
def.after_place(pos, rotation, pr, def.after_place_param)
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
local loaded_schematic = loadstring(minetest.serialize_schematic(schematic, "lua", {lua_use_comments = false, lua_num_indent_spaces = 0}) .. " return schematic")()
|
||||||
|
if not loaded_schematic then
|
||||||
|
minetest.log('warning', '[mcl_structures] Schematic ' .. schematic .. ' load serialized string problem at ' .. minetest.pos_to_string(pos))
|
||||||
|
return
|
||||||
|
end
|
||||||
|
local size = loaded_schematic.size
|
||||||
|
if not size then
|
||||||
|
minetest.log('warning', '[mcl_structures] Schematic ' .. schematic .. ' has no size at ' .. minetest.pos_to_string(pos))
|
||||||
|
return
|
||||||
|
end
|
||||||
|
local size_x, size_y, size_z = size.x, size.y, size.z
|
||||||
|
if rotation == "90" or rotation == "270" then
|
||||||
|
size_x, size_z = size_z, size_x
|
||||||
|
end
|
||||||
|
local x, y, z = pos.x, pos.y, pos.z
|
||||||
|
local p1 = {x = x, y = y, z = z}
|
||||||
|
local p2 = {x = x + size_x - 1, y = y + size_y - 1, z = size_z - 1}
|
||||||
|
minetest.log("verbose", "[mcl_structures] Emerge area " .. minetest.pos_to_string(p1) .. " - " .. minetest.pos_to_string(p2)
|
||||||
|
.. " of size " ..minetest.pos_to_string(size) .. " to place " .. schematic .. ", rotation " .. tostring(rotation))
|
||||||
|
local ecb_param = {
|
||||||
|
pos = vector.new(pos),
|
||||||
|
schematic = loaded_schematic,
|
||||||
|
rotation = rotation,
|
||||||
|
replacements = replacements,
|
||||||
|
force_placement = force_placement,
|
||||||
|
flags = flags,
|
||||||
|
after_place = after_place,
|
||||||
|
size = vector.new(size),
|
||||||
|
pr = pr,
|
||||||
|
param = param,
|
||||||
|
}
|
||||||
|
minetest.emerge_area(p1, p2, ecb_place, ecb_param)
|
||||||
end
|
end
|
||||||
|
|
||||||
function mcl_structures.get_struct(file)
|
function mcl_structures.get_struct(file)
|
||||||
|
@ -124,7 +193,12 @@ end
|
||||||
function mcl_structures.generate_desert_well(pos, rot)
|
function mcl_structures.generate_desert_well(pos, rot)
|
||||||
local newpos = {x=pos.x,y=pos.y-2,z=pos.z}
|
local newpos = {x=pos.x,y=pos.y-2,z=pos.z}
|
||||||
local path = modpath.."/schematics/mcl_structures_desert_well.mts"
|
local path = modpath.."/schematics/mcl_structures_desert_well.mts"
|
||||||
return mcl_structures.place_schematic(newpos, path, rot or "0", nil, true)
|
return mcl_structures.place_schematic({
|
||||||
|
pos = newpos,
|
||||||
|
schematic = path,
|
||||||
|
rotation = rot or "0",
|
||||||
|
force_placement = true
|
||||||
|
})
|
||||||
end
|
end
|
||||||
|
|
||||||
function mcl_structures.generate_igloo(pos, rotation, pr)
|
function mcl_structures.generate_igloo(pos, rotation, pr)
|
||||||
|
@ -227,7 +301,7 @@ end
|
||||||
|
|
||||||
function mcl_structures.generate_igloo_top(pos, pr)
|
function mcl_structures.generate_igloo_top(pos, pr)
|
||||||
-- FIXME: This spawns bookshelf instead of furnace. Fix this!
|
-- FIXME: This spawns bookshelf instead of furnace. Fix this!
|
||||||
-- Furnace does ot work atm because apparently meta is not set. :-(
|
-- Furnace does not work atm because apparently meta is not set. :-(
|
||||||
local newpos = {x=pos.x,y=pos.y-1,z=pos.z}
|
local newpos = {x=pos.x,y=pos.y-1,z=pos.z}
|
||||||
local path = modpath.."/schematics/mcl_structures_igloo_top.mts"
|
local path = modpath.."/schematics/mcl_structures_igloo_top.mts"
|
||||||
local rotation = tostring(pr:next(0,3)*90)
|
local rotation = tostring(pr:next(0,3)*90)
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
name = mcl_structures
|
name = mcl_structures
|
||||||
author = Wuzzy
|
author = Wuzzy, kay27
|
||||||
description = Structures for MCL2
|
description = Structures for MineClone 2/5
|
||||||
depends = mcl_loot
|
depends = mcl_loot, mcl_mapgen
|
||||||
|
|
|
@ -268,15 +268,13 @@ function settlements.place_schematics(settlement_info, pr)
|
||||||
local schematic = loadstring(schem_lua)()
|
local schematic = loadstring(schem_lua)()
|
||||||
-- build foundation for the building an make room above
|
-- build foundation for the building an make room above
|
||||||
-- place schematic
|
-- place schematic
|
||||||
mcl_structures.place_schematic(
|
mcl_structures.place_schematic({
|
||||||
pos,
|
pos = pos,
|
||||||
schematic,
|
schematic = schematic,
|
||||||
rotation,
|
rotation = rotation,
|
||||||
nil,
|
force_placement = true,
|
||||||
true,
|
on_place = init_nodes,
|
||||||
nil,
|
pr = pr,
|
||||||
init_nodes,
|
})
|
||||||
pr
|
|
||||||
)
|
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
Loading…
Reference in New Issue