basic stair, slab, wall, fence implementation

This commit is contained in:
wsor 2021-05-07 20:25:06 -04:00
parent 4c798100d1
commit b0b4856db9
14 changed files with 382 additions and 10 deletions

View File

@ -23,3 +23,5 @@ cd into repo, checkout main
links: links:
https://minetest.gitlab.io/minetest/helper-functions/ https://minetest.gitlab.io/minetest/helper-functions/
https://forum.minetest.net/viewtopic.php?f=9&t=26046 https://forum.minetest.net/viewtopic.php?f=9&t=26046
Aspect-oriented programming

View File

@ -21,10 +21,12 @@ local function register_ore(name, block_groups)
"desert_stone" "desert_stone"
} }
for _, bm in pairs(base_material) do for _, bm in pairs(base_material) do
local sgp = table.copy(minetest.registered_nodes["fl_stone:" .. bm]["groups"])
sgp.stairable, sgp.wallable = nil, nil
minetest.register_node("fl_ores:" .. name .. "_in_" .. bm, { minetest.register_node("fl_ores:" .. name .. "_in_" .. bm, {
description = name .. " in " .. bm, description = name .. " in " .. bm,
tiles = {"farlands_" .. bm .. ".png^farlands_" .. name .. "_overlay.png"}, tiles = {"farlands_" .. bm .. ".png^farlands_" .. name .. "_overlay.png"},
groups = minetest.registered_nodes["fl_stone:" .. bm]["groups"], groups = sgp,
drop = "fl_ores:" .. name .. "_ore", drop = "fl_ores:" .. name .. "_ore",
}) })

1
mods/fl_stairs/api.txt Normal file
View File

@ -0,0 +1 @@
change drop items drops itself, or uses full node nodedef.drop.stairs.type

140
mods/fl_stairs/init.lua Normal file
View File

@ -0,0 +1,140 @@
--note that this does not support hardware coloring as well as some other stuff
fl_stairs = {}
fl_stairs.details = {
version = 5,
name = "fl_stairs",
author = "wsor",
license = "MIT",
}
local stairtable = {
{
"slab",
{-0.5, -0.5, -0.5, 0.5, 0, 0.5},
},
{
"stair",
{
{-0.5, -0.5, -0.5, 0.5, 0.0, 0.5},
{-0.5, 0.0, 0.0, 0.5, 0.5, 0.5},
},
},
{
"inner_stair",
{
{-0.5, -0.5, -0.5, 0.5, 0.0, 0.5},
{-0.5, 0.0, 0.0, 0.5, 0.5, 0.5},
{-0.5, 0.0, -0.5, 0.0, 0.5, 0.0},
},
},
{
"outer_stair",
{
{-0.5, -0.5, -0.5, 0.5, 0.0, 0.5},
{-0.5, 0.0, 0.0, 0.0, 0.5, 0.5},
},
},
}
local function slab_onplace(itemstack, placer, pointed_thing)
if pointed_thing.type ~= "node" then return itemstack end
if minetest.get_node(pointed_thing.under).name == itemstack:get_name() and not placer:get_player_control().sneak then
minetest.set_node(pointed_thing.under, {name=string.sub(itemstack:get_name(), 1, -6)})
if minetest.is_creative_enabled(placer:get_player_name()) == false then
itemstack:take_item()
end
return itemstack
end
minetest.rotate_and_place(itemstack, placer, pointed_thing, true, {force_facedir = true}, true)
end
local function sstiles(nodedef, dtype)
local t = nodedef.tiles[dtype] or nodedef.tiles
if string.sub(nodedef.drawtype, 1, 5) == "glass" and t[2] then
local j = {{name = t[1] .. "^" .. t[2]}}
j[1].align_style = nodedef._disable_worldaligned and "node" or "world"
return j
end
for i = 1, #t do
if type(t[i]) == "string" then
t[i] = {name = t[i]}
end
t[i].align_style = nodedef._disable_worldaligned and "node" or "world"
end
return t
end
function fl_stairs.register_stairslab(itemstring)
local nodedef = minetest.registered_nodes[itemstring]
local paramtype2 = "facedir"
if nodedef.palette then paramtype2 = "colorfacedir" end
for _, stairinfo in pairs(stairtable) do
local regnode = itemstring .. "_" .. stairinfo[1]
local groups = table.copy(nodedef.groups)
groups[stairinfo[1]] = 1
groups.stairable, groups.wallable, groups.not_in_creative_inventory = nil, nil, 1
minetest.register_node(":" .. regnode, {
description = nodedef.description .. " " .. stairinfo[1],
tiles = sstiles(nodedef, "_" .. stairinfo[1]),
paramtype = "light",
paramtype2 = paramtype2,
palette = nodedef.palette,
use_texture_alpha = nodedef.use_texture_alpha,
drawtype = "nodebox",
node_box = {
type = "fixed",
fixed = stairinfo[2],
},
on_place = function(itemstack, placer, pointed_thing)
if stairinfo[1] == "slab" then
slab_onplace(itemstack, placer, pointed_thing)
else
minetest.rotate_node(itemstack, placer, pointed_thing)
end
end,
drop = nodedef.drop and nodedef.drop.stairs and nodedef.drop.stairs[stairinfo[1]],
groups = groups,
})
end
end
function fl_stairs.register_wall(itemstring)
local nodedef = minetest.registered_nodes[itemstring]
local groups = table.copy(nodedef.groups)
groups. stairable, groups.wallable, groups.wall, groups.not_in_creative_inventory = nil, nil, 1, 1
minetest.register_node(":" .. itemstring .. "_wall", {
description = nodedef.description .. " wall",
tiles = nodedef.tiles,
paramtype = "light",
drawtype = "nodebox",
node_box = {
type = "connected",
fixed = {-1/4, -1/2, -1/4, 1/4, 1/2, 1/4},
connect_front = {-3/16, -1/2, -1/2, 3/16, 3/8, -1/4},
connect_left = {-1/2, -1/2, -3/16, -1/4, 3/8, 3/16},
connect_back = {-3/16, -1/2, 1/4, 3/16, 3/8, 1/2},
connect_right = { 1/4, -1/2, -3/16, 1/2, 3/8, 3/16},
},
connects_to = {"group:wall", "group:wood_related", "group:stonelike"},
drop = nodedef.drop and nodedef.drop.walls,
groups = groups,
})
end
minetest.register_on_mods_loaded(function()
for _, node in pairs(minetest.registered_nodes) do
if node.groups.stairable == 1 then
fl_stairs.register_stairslab(node.name)
end
if node.groups.wallable == 1 then
fl_stairs.register_wall(node.name)
end
end
end)

1
mods/fl_stairs/mod.conf Normal file
View File

@ -0,0 +1 @@
depends = fl_stone, fl_glass, fl_bricks, fl_trees

View File

@ -1,30 +1,47 @@
local modpath = minetest.get_modpath("fl_stone") local modpath = minetest.get_modpath("fl_stone")
dofile(modpath .. "/other.lua") dofile(modpath .. "/other.lua")
local function create_stone_types(name, groups) local function create_stone_types(name, rgroups, sgroups, blgroups, brgroups)
local gp = groups or {oddly_breakable_by_hand = 3} local rgp = rgroups or {oddly_breakable_by_hand = 3, stairable = 1, wallable = 1, stonelike = 1}
local sgp = sgroups or {oddly_breakable_by_hand = 3, stairable = 1, wallable = 1, stonelike = 1, stone = 1}
local blgp = blgroups or {oddly_breakable_by_hand = 3, stairable = 1, stonelike = 1}
local brgp = brgroups or {oddly_breakable_by_hand = 3, stairable = 1, wallable = 1, stonelike = 1}
local rn = "fl_stone:" .. name .. "_rubble"
--node registration --node registration
minetest.register_node("fl_stone:" .. name .. "_rubble", { minetest.register_node("fl_stone:" .. name .. "_rubble", {
description = name .. " rubble", description = name .. " rubble",
tiles = {"farlands_" .. name .. "_rubble.png"}, tiles = {"farlands_" .. name .. "_rubble.png"},
groups = gp, groups = rgp,
}) })
minetest.register_node("fl_stone:" .. name, { minetest.register_node("fl_stone:" .. name, {
description = name, description = name,
tiles = {"farlands_" .. name .. ".png"}, tiles = {"farlands_" .. name .. ".png"},
drop = "fl_terrain:" .. name .. "_rubble", --drop = "fl_stone:" .. name .. "_rubble",
groups = gp, drop = {
max_items = 1,
items = {
{items = {rn}}
},
stairs = {
slab = rn .. "_slab",
stair = rn .. "_stair",
inner_stair = rn .. "_inner_stair",
outer_stair = rn .. "_outer_stair",
},
walls = rn .. "_wall"
},
groups = sgp,
}) })
minetest.register_node("fl_stone:" .. name .. "_block", { minetest.register_node("fl_stone:" .. name .. "_block", {
description = name .. " block", description = name .. " block",
tiles = {"farlands_" .. name .. "_block.png"}, tiles = {"farlands_" .. name .. "_block.png"},
groups = gp, groups = blgp,
}) })
minetest.register_node("fl_stone:" .. name .. "_brick", { minetest.register_node("fl_stone:" .. name .. "_brick", {
description = name .. " brick", description = name .. " brick",
tiles = {"farlands_" .. name .. "_brick.png"}, tiles = {"farlands_" .. name .. "_brick.png"},
groups = gp, groups = brgp,
}) })
--craft registration --craft registration

View File

@ -102,6 +102,8 @@ local function shelf_nodes(name)
local group = table.copy(minetest.registered_nodes["fl_trees:" .. name .. "_plank"]["groups"]) local group = table.copy(minetest.registered_nodes["fl_trees:" .. name .. "_plank"]["groups"])
group[overlay .. "_shelf"] = 1 group[overlay .. "_shelf"] = 1
group["plank"] = nil group["plank"] = nil
group["stairable"] = nil
group["fenceable"] = nil
minetest.register_node("fl_storage:" .. name .. "_" .. overlay .. "_shelf", { minetest.register_node("fl_storage:" .. name .. "_" .. overlay .. "_shelf", {
description = name .. " " .. overlay .. " shelf", description = name .. " " .. overlay .. " shelf",

View File

@ -0,0 +1,10 @@
local modpath = minetest.get_modpath("fl_tool_nodes")
local tool_nodes = {
"saw",
--"furnace",
}
for _, tool in pairs(tool_nodes) do
dofile(modpath .. "/" .. tool .. ".lua")
end

179
mods/fl_tool_nodes/saw.lua Normal file
View File

@ -0,0 +1,179 @@
local function updateformspec(pos, clicker)
--vars for stuff
local chName = "saw"
local iPos = pos.x .. "," .. pos.y .. "," .. pos.z
local cInvSize = clicker:get_inventory():get_size("main")
local rLength = (cInvSize-9)/3
local slotSize
local formSize
if rLength == 12 then slotSize, formSize = 0.725, "10.4,7.475"
elseif rLength == 11 then slotSize, formSize = 0.8, "10.4,7.7"
elseif rLength == 10 then slotSize, formSize = 0.89, "10.4,7.97"
else slotSize, formSize = 1, "10.4,8.3" end
--header of formspec
local formspec = {
"formspec_version[4]",
"size[" .. formSize .. "]",
"no_prepend[]",
"style_type[box;colors=#77777710,#77777710,#777,#777]",
"style_type[list;size=1;spacing=0.1]",
"listcolors[#0000;#ffffff20]",
"bgcolor[black;neither]",
"background9[0,0;" .. formSize .. ";i3_bg_full.png;false;10]",
"label[0.3,0.4;" .. chName .. "]",
"box[1,1.2;1,1;]",
"list[nodemeta:" .. iPos .. ";main;1,1.2;1,1;]",
--"style_type[image_button,item_image_button;border=false]",
"image[2.5,1.2;1,1;i3_arrow.png]",
}
for i=0, 1 do
for j=0, 3 do
table.insert(formspec, "image[" .. 4+j+(j*0.1) .. "," .. 0.6+i+(i*0.1) .. ";1,1;i3_slot.png]")
end
end
local inv = minetest.get_inventory({type = "node", pos = pos})
if not inv:is_empty("main") and inv:get_stack("main", 1):get_count() >= 6 then
local stack = inv:get_stack("main", 1)
--minetest.chat_send_all(stack:get_name())
local node_table = {}
if minetest.get_item_group(stack:get_name(), "stairable") ~= 0 then
table.insert(node_table, {stack:get_name(), "slab", 4})
table.insert(node_table, {stack:get_name(), "stair", 2})
table.insert(node_table, {stack:get_name(), "outer_stair", 3})
table.insert(node_table, {stack:get_name(), "inner_stair", 1})
end
if minetest.get_item_group(stack:get_name(), "fenceable") ~= 0 then
table.insert(node_table, {stack:get_name(), "fence", 4})
end
if minetest.get_item_group(stack:get_name(), "wallable") ~= 0 then
table.insert(node_table, {stack:get_name(), "wall", 2})
end
if minetest.get_item_group(stack:get_name(), "stone") ~= 0 then
table.insert(node_table, {stack:get_name(), "block", 1})
end
table.insert(formspec, "style_type[item_image_button;border=false]")
table.insert(formspec, "style_type[item_image_button;bgimg_hovered=i3_slot.png]")
local x = 0
local y = 0
for i = 1, #node_table do
if x==4 then x=0 y=1 end
local nm = ItemStack(node_table[i][1] .. "_" .. node_table[i][2])
nm:set_count(node_table[i][3])
nm = nm:to_string()
table.insert(formspec, "item_image_button[" .. 4+x+(x*0.1) .. "," .. 0.6+y+(y*0.1) .. ";1,1;" .. nm .. ";" .. node_table[i][2] .. ";]")
x=x+1
end
end
--build inventory part of formspec
table.insert(formspec, "label[0.3,3.4;Inventory]")--5.4
table.insert(formspec, "style_type[box;colors=#77777710,#77777710,#777,#777]")
for i=0, 8 do
table.insert(formspec, "box[" .. 0.3+i+(i*0.1) ..",3.7;1,1;]")
end
table.insert(formspec, "list[current_player;main;0.3,3.7;9,1;]")
table.insert(formspec, "style_type[list;size=" .. slotSize .. ";spacing=0.1]")
table.insert(formspec, "style_type[box;colors=#666]") -- change bottom 3 rows color
for i=0, 2 do
for j=0, rLength-1 do
table.insert(formspec, "box[" .. 0.3+(j*0.1)+(j*slotSize) .."," .. 4.8+(i*0.1)+(i*slotSize) .. ";"
.. slotSize .. "," .. slotSize .. ";]")
end
table.insert(formspec, "list[current_player;main;0.3," .. 4.8+(i*0.1)+(i*slotSize) .. ";"
.. rLength .. ",1;" .. 9+(rLength*i) .. "]")
end
--enable shiftclicking?
table.insert(formspec, "listring[nodemeta:" .. iPos .. ";main]")
table.insert(formspec, "listring[current_player;main]")
--show formspec
local saw_formspec = table.concat(formspec, "")
--this breaks recieving fields
--minetest.show_formspec(clicker:get_player_name(), "fl_stairs:saw_formspec", saw_formspec)
local meta = minetest.get_meta(pos)
meta:set_string("formspec", saw_formspec)
end
--textures and nodebox are temperary and suck
minetest.register_node(":fl_stairs:tablesaw", {
description = "table saw",
tiles = {
"farlands_apple_planks.png^farlands_saw_top.png",
"farlands_apple_planks.png^farlands_saw_bottom.png",
"farlands_apple_planks.png^farlands_saw_side.png"
},
groups = {oddly_breakable_by_hand = 3},
drawtype = "nodebox",
node_box = {
type = "fixed",
fixed = {
{-0.5, -0.5, -0.5, 0.5, 0.125, 0.5},--base
{-0.01, -0.125, -0.3125, 0.01, 0.25, 0.3125},
{-0.01, 0.25, -0.25, 0.01, 0.3125, 0.25},
{-0.01, 0.3125, -0.1875, 0.01, 0.375, 0.1875},
--{-0.01, 0.375, -0.125, 0.01, 0.4375, 0.125},
{-0.01, 0.375, -0.0625, 0.01, 0.4375, 0.0625}
--{-0.01, 0.4375, -0.0625, 0.01, 0.5, 0.0625} --top
}
},
on_construct = function(pos)
local inv = minetest.get_meta(pos):get_inventory()
inv:set_size("main", 1)
end,
on_rightclick = function(pos, node, clicker, itemstack, pointed_thing)
updateformspec(pos, clicker)
end,
allow_metadata_inventory_put = function(pos, listname, index, stack, player)
local get_group = minetest.get_item_group
if get_group(stack:get_name(), "stairable") ~= 0
or get_group(stack:get_name(), "fenceable") ~= 0
or get_group(stack:get_name(), "wallable") ~= 0 then
return stack:get_count()
end
return 0
end,
on_receive_fields = function(pos, formname, fields, sender)
--minetest.chat_send_all("triggered")
--minetest.chat_send_all(dump(fields))
local function add_item(item, gcount, tcount)
local inv = sender:get_inventory()
local saw_inv = minetest.get_inventory({type = "node", pos = pos})
local saw_stack = saw_inv:get_stack("main", 1)
local stack = ItemStack(saw_stack:get_name() .. item)
stack:set_count(gcount)
if inv:room_for_item("main", stack) then
inv:add_item("main", stack)
saw_stack:take_item(tcount)
saw_inv:set_stack("main", 1, saw_stack)
updateformspec(pos, sender)
end
end
if fields.inner_stair then add_item("_inner_stair", 1, 1)
elseif fields.outer_stair then add_item("_outer_stair", 3, 1)
elseif fields.stair then add_item("_stair", 2, 1)
elseif fields.slab then add_item("_slab", 4, 1)
elseif fields.block then add_item("_block", 1, 6)
elseif fields.fence then add_item("_fence", 4, 1)
elseif fields.wall then add_item("_wall", 2, 1)
end
end,
on_metadata_inventory_put = function(pos, listname, index, stack, player)
updateformspec(pos, player)
end,
on_metadata_inventory_take = function(pos, listname, index, stack, player)
updateformspec(pos, player)
end,
on_dig = function(pos, node, digger)
local inv = minetest.get_inventory({type="node", pos=pos})
for _, item in ipairs(inv:get_list("main")) do
minetest.add_item(pos, item)
end
minetest.node_dig(pos, node, digger)
end,
})

Binary file not shown.

After

Width:  |  Height:  |  Size: 528 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 783 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 534 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 539 B

View File

@ -1,7 +1,9 @@
local function tree_nodes(name, tgroup, lgroup, pgroup) local function tree_nodes(name, tgroup, lgroup, pgroup)
local tgp = tgroup or {oddly_breakable_by_hand = 3, wood_related = 1, tree = 1, trunk = 1} local tgp = tgroup or {oddly_breakable_by_hand = 3, wood_related = 1, tree = 1, trunk = 1}
local lgp = lgroup or {oddly_breakable_by_hand = 3, wood_related = 1, tree = 1, leaf = 1} local lgp = lgroup or {oddly_breakable_by_hand = 3, wood_related = 1, tree = 1, leaf = 1}
local pgp = pgroup or {oddly_breakable_by_hand = 3, wood_related = 1, plank = 1} local pgp = pgroup or {oddly_breakable_by_hand = 3, wood_related = 1, plank = 1, fenceable = 1, stairable = 1}
local fgp = table.copy(pgp)
fgp.stairable, fgp.fenceable, fgp.fence, fgp.not_in_creative_inventory = nil, nil, 1, 1
minetest.register_node("fl_trees:" .. name .. "_trunk", { minetest.register_node("fl_trees:" .. name .. "_trunk", {
--nodes --nodes
@ -30,6 +32,22 @@ local function tree_nodes(name, tgroup, lgroup, pgroup)
groups = pgp, groups = pgp,
on_place = minetest.rotate_node on_place = minetest.rotate_node
}) })
minetest.register_node("fl_trees:" .. name .. "_plank_fence", {
description = name .. " fence",
paramtype = "light",
drawtype = "nodebox",
node_box = {
type = "connected",
fixed = {-1/8, -1/2, -1/8, 1/8, 1/2, 1/8},
connect_front = {{-1/16, 3/16, -1/2, 1/16, 5/16, -1/8 }, {-1/16, -5/16, -1/2, 1/16, -3/16, -1/8 }},
connect_left = {{-1/2, 3/16, -1/16, -1/8, 5/16, 1/16}, {-1/2, -5/16, -1/16, -1/8, -3/16, 1/16}},
connect_back = {{-1/16, 3/16, 1/8, 1/16, 5/16, 1/2 }, {-1/16, -5/16, 1/8, 1/16, -3/16, 1/2 }},
connect_right = {{ 1/8, 3/16, -1/16, 1/2, 5/16, 1/16}, { 1/8, -5/16, -1/16, 1/2, -3/16, 1/16}},
},
connects_to = {"group:fence", "group:wood_related"},
tiles = {"farlands_" .. name .. "_planks.png"},
groups = fgp,
})
--crafts --crafts
minetest.register_craft({ minetest.register_craft({