working orange trees, not factored

master
Izzy 2020-04-30 22:38:09 -06:00
parent 5acebec719
commit cdfbe8e279
14 changed files with 605 additions and 53 deletions

196
api.lua
View File

@ -689,3 +689,199 @@ farming_super.register_plant = function(name, def)
}
return r
end
-- plants with hardware above ground, like tomatoes
farming_super.register_rooted_plant = function(name, def)
local mname = name:split(":")[1]
local pname = name:split(":")[2]
local def_drops = def.drops or {}
-- Check def table
if not def.description then
def.description = "Seed"
end
if not def.inventory_image then
def.inventory_image = "unknown_item.png"
end
if not def.steps then
return nil
end
if type(def.steps) == "number" then
def.steps = {def.steps}
end
if not def.minlight then
def.minlight = 1
end
if not def.maxlight then
def.maxlight = 14
end
if not def.fertility then
def.fertility = {}
end
if def.place_param2 == "plus" then
def.place_param2 = 1
elseif def.place_param2 == "hex" then
def.place_param2 = 2
elseif def.place_param2 == "hatch" or def.place_param2 == "#" then
def.place_param2 = 3 -- the shape of #
elseif def.place_param2 == "V" or def.place_param2 == "v" then
def.place_param2 = 4 -- used by dry_shrub
elseif def.place_param2 == "X" or def.place_param2 == "x" then
def.place_param2 = 0 -- regular plants
end
local base_plant = mname .. ":" .. pname
def.step_len = def.step_len or {}
def.step_len[1] = def.step_len[1] or 1
-- Register seed -- attached node needs not be on 2nd tier nodes
local g = {seed = 1, snappy = 3, attached_node = 1, flammable = 2}
local g2 = {seed = 1, snappy = 3, flammable = 2}
for k, v in pairs(def.fertility) do
g[v] = 1
g2[v] = 1
end
for k, v in pairs(def.groups) do
g[k] = v
g2[k] = v
end
if not def.no_harvest then
-- Register harvest
local h_def = {
description = pname:gsub("^%l", string.upper),
inventory_image = mname .. "_" .. pname .. ".png",
groups = {flammable = 2},
}
if def.eat_value ~= nil then
h_def.on_use = minetest.item_eat(def.eat_value)
end
minetest.register_craftitem(":" .. mname .. ":" .. pname, h_def)
end
local next_node = {
[mname .. ":seed_" .. pname] = mname .. ":" .. pname .. "_1_1"
}
local stack_height = {
[mname .. ":seed_" .. pname] = 1
}
local last = nil
local totalSteps = 0
for _,numSteps in ipairs(def.steps) do
totalSteps = totalSteps + numSteps
end
def.last_step = totalSteps
-- print("total steps " .. totalSteps)
local tex_base = mname.."_"..pname
if def.textures and def.textures.base then
tex_base = def.textures.base
end
local name = mname .. ":" .. pname .. "_"..step.."_"..tier
local dropname = "p"..tierCount.."s"..tierStep.."t"..tier
local drops = def_drops[dropname] or def.default_drop
local tex = (def.textures and def.textures[dropname]) or (tex_base.."_"..tierCount.."_"..tierStep.."_"..tier..".png")
local gg = g2
if tier == 1 then
gg = g
end
local height = -0.4
if tierCount > 1 and tier < tierCount then
height = 0.5
end
def.step_len[step+1] = def.step_len[step+1] or 1
local sbox = {
type = "fixed",
fixed = {-0.5, -0.5, -0.5, 0.5, -0.25, 0.5},
}
if tierCount > 1 then
sbox = {
type = "fixed",
fixed = {-5 / 16, -0.5, -5 / 16, 5 / 16, height, 5 / 16},
}
end
minetest.register_node(name, {
description = "Hops Plant",
drawtype = "plantlike_rooted",
-- waving = 1,
tiles = {"default_dirt.png^farming_soil_wet.png", "default_dirt.png^farming_soil_wet_side.png"},
drop = "default:dirt",
special_tiles = {{name = "farming_super_hops_vine.png", tileable_vertical = true}},
inventory_image = "farming_super_hops_vine.png",
paramtype = "light",
paramtype2 = "leveled",
place_param2 = 1,
groups = {snappy = 3},
visual_scale = 1.5,
selection_box = {
type = "fixed",
fixed = {
{-0.5, -0.5, -0.5, 0.5, 0.5, 0.5},
{-2/16, 0.5, -2/16, 2/16, 3.5, 2/16},
},
},
node_dig_prediction = "default:sand",
node_placement_prediction = "",
sounds = default.node_sound_sand_defaults({
dig = {name = "default_dig_snappy", gain = 0.2},
dug = {name = "default_grass_footstep", gain = 0.25},
}),
after_destruct = function(pos, oldnode)
local n = minetest.get_node(pos)
-- if n.name == "farming_super:hops_vine_fruit" then
-- minetest.set_node(pos, {name = "farming_super:hops_vine", param2 = oldnode.param2})
if n.name ~= "farming_super:hops_vine_fruit" then
minetest.set_node(pos, {name = "farming:soil_wet"})
end
end,
})
def.next_node = next_node
-- print("def name "..pname)
farming_super.registered_plants[base_plant] = def
if not def.no_seed then
local old_grass_drops = deepclone(minetest.registered_items["default:junglegrass"].drop)
-- print('+++++++++++++++++++++++++++++++++++++++++++')
table.insert(old_grass_drops.items, 1, {items={mname .. ":seed_" .. pname}, rarity=2})
table.sort(old_grass_drops.items, function(a, b) return (b.rarity or 0) < (a.rarity or 0) end)
minetest.override_item("default:junglegrass", {drop = old_grass_drops})
-- print(dump(minetest.registered_items["default:junglegrass"]))
end
-- Return
local r = {
seed = mname .. ":seed_" .. pname,
harvest = mname .. ":" .. pname
}
return r
end

View File

@ -2,7 +2,16 @@
--[[
TODO:
tension physics on wires
spots/bugs disease
check nearby nodes for yellowing decision
growth and aging of vines
]]
local grape_speed = {
@ -182,7 +191,9 @@ for gi,color in ipairs(colors) do
{ items = {'farming_super:grape_cutting_'..color}, rarity = 2 },
}
},
groups = {snappy = 1, choppy=2, flammable = 1, grape_stem = 1, not_in_creative_inventory=1},
groups = {
snappy = 1, choppy=2, flammable = 1, grape_stem = 1, not_in_creative_inventory=1,
},
sounds = default.node_sound_leaves_defaults(),
selection_box = {
type = "fixed",
@ -211,7 +222,10 @@ for gi,color in ipairs(colors) do
sunlight_propagates = true,
-- walkable = false,
climbable = true,
groups = {snappy=1, flammable=1, grape_leaves=1, grape_leaves_bare=1, grape_healthy_leaves=1, not_in_creative_inventory=1},
groups = {
snappy=1, flammable=1, grape_leaves=1, grape_leaves_bare=1,
grape_healthy_leaves=1, not_in_creative_inventory=1, hangs_from_vines=1,
},
grape_color = color,
drop = {
max_items = 2,
@ -253,7 +267,10 @@ for gi,color in ipairs(colors) do
-- walkable = false,
climbable = true,
grape_color = color,
groups = {snappy=1, flammable=1, grape_leaves=1, grape_yellow_leaves=1, not_in_creative_inventory=1},
groups = {
snappy=1, flammable=1, grape_leaves=1, grape_yellow_leaves=1,
not_in_creative_inventory=1, hangs_from_vines=1
},
sounds = default.node_sound_leaves_defaults(),
selection_box = {
type = "fixed",
@ -278,7 +295,10 @@ for gi,color in ipairs(colors) do
-- walkable = true,
climbable = true,
grape_color = color,
groups = {snappy=1, flammable=1, grape_leaves=1, grape_healthy_leaves=1, not_in_creative_inventory=1},
groups = {
snappy=1, flammable=1, grape_leaves=1, grape_healthy_leaves=1,
not_in_creative_inventory=1, hangs_from_vines=1
},
sounds = default.node_sound_leaves_defaults(),
drop = {
max_items = 2,
@ -539,8 +559,8 @@ minetest.register_abm({
minetest.register_abm({
label = "Grape Leaf Disease Origin",
nodenames = {"group:grape_healthy_leaves"},
interval = 120,
chance = 500,
interval = 440,
chance = 900,
action = function(pos)
local node = minetest.get_node(pos)
local color = minetest.registered_nodes[node.name].grape_color

View File

@ -41,7 +41,6 @@ minetest.register_node("farming_super:hops_vine", {
description = "Hops Plant",
drawtype = "plantlike_rooted",
waving = 1,
tiles = {"default_sand.png"},
tiles = {"default_dirt.png^farming_soil_wet.png", "default_dirt.png^farming_soil_wet_side.png"},
drop = "default:dirt",
special_tiles = {{name = "farming_super_hops_vine.png", tileable_vertical = true}},

View File

@ -8,6 +8,7 @@ dofile(modpath.."/api.lua")
dofile(modpath.."/vines.lua")
dofile(modpath.."/hops.lua")
dofile(modpath.."/grapes.lua")
dofile(modpath.."/trees.lua")
@ -69,17 +70,31 @@ sugar processing
TODO: core
pests
pests, locusts like butterflies
stick or strings for plants to grow on
wilting on low water
dead version of all plants
yellowing on bad soil
fruit trees
apple, proper
all citrus
pears
durian, jackfruit
fruit flies
rotten fruit on the ground
tree hybrids
smudge pots
vinegar
scythe for harvesting larger squares
better solution for excessive hoe clicking
drop-in replacement for farming_plus
BUGS:
seed will move to first stage without wet soil
fix on_place to not re-place the same plant and waste inventory
]]
@ -1101,6 +1116,30 @@ minetest.register_decoration({
dofile(modpath.."/crafts.lua")
minetest.register_node("farming_super:test", {
description = "Tester",
drawtype = "plantlike",
-- waving = 1,
-- visual_scale = 1.69,
tiles = {"farming_super_trellis.png"},
inventory_image = "farming_super_test.png",
paramtype = "light",
paramtype2 = "meshoptions",
sunlight_propagates = true,
-- walkable = false,
buildable_to = false,
grape_color = color,
groups = {snappy = 2, plant=1, oddly_breakable_by_hand = 1, },
sounds = default.node_sound_leaves_defaults(),
selection_box = {
type = "fixed",
fixed = {-4 / 16, -0.5, -4 / 16, 4 / 16, 0.5, 4 / 16},
},
collision_box = {
type = "fixed",
fixed = {-4 / 16, -0.5, -4 / 16, 4 / 16, 0.5, 4 / 16},
},
place_param2 = 3,
})

View File

@ -146,3 +146,21 @@ minetest.register_craft({
})
minetest.register_abm({
label = "fall from vines",
nodenames = {"group:hangs_from_vines"},
interval = 20,
chance = 10,
action = function(pos, node)
pos.y = pos.y + 1
local wire = minetest.get_node(pos)
if wire.name ~= "farming_super:wire" then
pos.y = pos.y - 1
minetest.set_node(pos, {name = "air"})
end
end,
})

Binary file not shown.

After

Width:  |  Height:  |  Size: 569 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 396 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 426 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 540 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 462 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 573 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 671 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 163 B

368
trees.lua
View File

@ -3,9 +3,13 @@
local orange_speed = {
retry = 30,
sapling = 10,
rand = 2,
}
local function gr()
return math.random(orange_speed.rand)
end
-- follow tree trunks down to the root
local function find_bottom(pos)
@ -27,33 +31,126 @@ local function find_bottom(pos)
end
local function advance_trunk(pos)
local stage_data = {
[1] = {
ymin = 1, ymax=2, ysquash = 2, yoff = 2,
xrange = 1, zrange = 1,
rand = .2,
dist = 1.1,
time = 10,
},
[2] = {
ymin = 1, ymax=3, ysquash = 2, yoff = 2,
xrange = 2, zrange = 2,
rand = .6,
dist = 1.2,
time = 15,
},
[3] = {
ymin = 1, ymax=5, ysquash = 2, yoff = 2,
xrange = 3, zrange = 3,
rand = 1,
dist = 1.6,
time = 10,
},
[4] = {
ymin = 1, ymax=6, ysquash = 2, yoff = 2,
xrange = 3, zrange = 3,
rand = 1,
dist = 1.9,
time = 15,
},
[5] = {
ymin = 1, ymax = 7, ysquash = 2, yoff = 2,
xrange = 4, zrange = 4,
rand = 1,
dist = 2.1,
time = 10,
},
[6] = {
ymin = 1, ymax = 8, ysquash = 2, yoff = 2,
xrange = 4, zrange = 4,
rand = 1.1,
dist = 2.5,
},
}
local function advance_trunk(pos, elapsed)
local meta = minetest.get_meta(pos)
local stage = meta:get_int("stage")
if stage == 0 then stage = 1 end
local m = stage_data[stage]
if stage >= 6 then
stage = 6
else
-- calculate how many steps should have elapsed
while elapsed > m.time + orange_speed.rand do
elapsed = m.time + orange_speed.rand
stage = stage + 1
if stage >= 6 then
stage = 6
break
end
m = stage_data[stage]
end
end
m = stage_data[stage]
local raw_trunks = meta:get_string("trunks")
local trunks = minetest.deserialize(raw_trunks)
local raw_leaves = meta:get_string("leaves")
local leaves = minetest.deserialize(raw_leaves)
minetest.set_node({x=pos.x, y=pos.y, z=pos.z}, {name="farming_super:tree_trunk_root_"..stage})
if not leaves then
leaves = {}
end
for _,v in ipairs(leaves) do
minetest.set_node(v, {name="air"})
end
for x = -m.xrange,m.xrange do
for y = m.ymin,m.ymax do
for z = -m.zrange,m.zrange do
local y2 = (y-m.yoff) / m.ysquash
local d = math.sqrt(x*x + z*z + y2*y2)
-- if d < (stage/2) + math.random() then
if d < m.dist + math.random() * m.rand then
local p = {x=pos.x+x, y=pos.y+y, z=pos.z+z}
local n = minetest.get_node(p)
if n.name == "air" then
minetest.set_node(p, {name="farming_super:tree_leaves_1"})
table.insert(leaves, p)
end
end
end
end
end
minetest.swap_node({x=pos.x, y=pos.y, z=pos.z}, {name="farming_super:tree_trunk_root_"..stage})
for i = 1,stage do
minetest.set_node({x=pos.x, y=pos.y+i, z=pos.z}, {name="farming_super:tree_trunk_"..stage})
end
meta:set_string("leaves", minetest.serialize(leaves))
meta:set_int("stage", stage + 1)
if stage < 5 then
minetest.get_node_timer(pos):start(2)
if stage < 6 then
minetest.get_node_timer(pos):start(m.time)
end
end
for sz = 1,5 do
for sz = 1,6 do
local q = sz * 1
minetest.register_node("farming_super:tree_trunk_root_"..sz, {
description = "Tree Root",
@ -70,7 +167,7 @@ for sz = 1,5 do
is_ground_content = false,
groups = {
tree = 1, choppy = 2, oddly_breakable_by_hand = 1, flammable = 2, plant = 1,
fs_tree_trunk = 1,
fs_tree_trunk = 1, tree_trunk_root_fertile = 1,
},
sounds = default.node_sound_wood_defaults(),
@ -82,7 +179,7 @@ for sz = 1,5 do
end,
on_timer = function(pos, elapsed)
advance_trunk(pos)
advance_trunk(pos, elapsed)
end,
@ -103,23 +200,172 @@ for sz = 1,5 do
is_ground_content = false,
groups = {
tree = 1, choppy = 2, oddly_breakable_by_hand = 1, flammable = 2, plant = 1,
fs_tree_trunk = 1,
fs_tree_trunk = 1,
},
sounds = default.node_sound_wood_defaults(),
on_place = minetest.rotate_node,
})
end
--[[
minetest.register_node("farming_super:orange_sapling_"..color, {
minetest.register_craftitem("farming_super:orange", {
description = "Oranges",
inventory_image = "farming_super_oranges_overlay_4.png",
on_use = minetest.item_eat(2),
groups = {flammable = 1},
})
minetest.register_node("farming_super:orange_seed", {
description = "Orange Seeds",
tiles = {"farming_super_oranges_seed.png"},
inventory_image = "farming_super_oranges_seed.png",
drawtype = "signlike",
groups = {seed = 1, snappy = 3, attached_node = 1, flammable = 2},
paramtype = "light",
paramtype2 = "wallmounted",
walkable = false,
sunlight_propagates = true,
selection_box = {
type = "fixed",
fixed = {-0.5, -0.5, -0.5, 0.5, -0.375, 0.5},
},
sounds = default.node_sound_dirt_defaults({
dig = {name = "", gain = 0},
dug = {name = "default_grass_footstep", gain = 0.2},
place = {name = "default_place_node", gain = 0.25},
}),
})
minetest.register_craft({
type = "shapeless",
output = "farming_super:orange_seed 3",
recipe = {"farming_super:orange", "group:sword"},
replacements = {
{"default:sword_wood", "default:sword_wood"},
{"default:sword_steel", "default:sword_steel"},
{"default:sword_bronze", "default:sword_bronze"},
{"default:sword_mese", "default:sword_mese"},
{"default:sword_diamond", "default:sword_diamond"},
},
})
local leaf_defs = {
"default_leaves.png",
"default_leaves.png^farming_super_flowers_overlay_w_y.png",
"default_leaves.png^farming_super_oranges_overlay_1.png",
"default_leaves.png^farming_super_oranges_overlay_2.png",
"default_leaves.png^farming_super_oranges_overlay_3.png",
"default_leaves.png^farming_super_oranges_overlay_4.png",
}
local leaf_drops = {
"farming_super:tree_leaves_1",
"farming_super:tree_leaves_1",
"farming_super:tree_leaves_1",
"farming_super:tree_leaves_1",
"farming_super:tree_leaves_1",
{
max_items = 1,
items = {
{items={--[["farming_super:tree_leaves_1",]] "farming_super:orange 2"}, rarity = 2},
{items={--[["farming_super:tree_leaves_1",]] "farming_super:orange 3"}, rarity = 4},
},
},
}
local leaf_punch = {
[6] = function(pos, node, puncher)
local inv = puncher:get_inventory()
local drops = minetest.get_node_drops(node.name)
for _,d in pairs(drops) do
inv:add_item("main", d)
end
minetest.set_node(pos, {name = "farming_super:tree_leaves_1",})
-- minetest.get_node_timer(pos):start(grape_speed.fruit + gr())
end,
}
local leaf_times = { -- time to get to the next stage
2,
3,
4,
5,
6,
7,
}
-- fruiting leaves
for i,d in pairs(leaf_defs) do
local def = {
description = "Tree Leaves",
drawtype = "allfaces_optional",
waving = 1,
tiles = {d},
special_tiles = {d},
paramtype = "light",
drop = leaf_drops[i],
is_ground_content = false,
groups = {snappy = 3, fs_leafdecay = 3, flammable = 2, leaves = 1},
sounds = default.node_sound_leaves_defaults(),
leaf_stage = i,
on_timer = function(pos, elapsed)
local node = minetest.get_node(pos)
local def = minetest.registered_nodes[node.name]
local stage = def.leaf_stage
if not stage or not leaf_times[stage+1] then
return
end
-- less fruit in the tree's interior
if stage == 1 then
local airs = minetest.find_nodes_in_area(
{x=pos.x-1, y=pos.y-1, z=pos.z-1},
{x=pos.x+1, y=pos.y+1, z=pos.z+1},
{"air"}
)
if #airs < 7 and math.random() < .75 then
return
end
end
stage = stage + 1
minetest.set_node(pos, {name="farming_super:tree_leaves_"..stage})
minetest.get_node_timer(pos):start(leaf_times[stage])
end,
on_place = function(itemstack, placer, pointed_thing)
local stack = minetest.rotate_node(itemstack, placer, pointed_thing)
minetest.get_node_timer(pointed_thing.above):start(leaf_times[i])
return stack
end,
}
if leaf_punch[i] ~= nil then
def.on_punch = leaf_punch[i]
end
minetest.register_node("farming_super:tree_leaves_"..i, def)
end
minetest.register_node("farming_super:orange_sapling", {
description = "Orange Sapling",
drawtype = "plantlike",
waving = 1,
-- visual_scale = 1.69,
tiles = {"farming_super_orange_sapling.png"},
inventory_image = "farming_super_orange_sapling.png",
tiles = {"farming_super_oranges_sapling.png"},
inventory_image = "farming_super_oranges_sapling.png",
paramtype = "light",
paramtype2 = "meshoptions",
sunlight_propagates = true,
@ -131,11 +377,11 @@ minetest.register_node("farming_super:orange_sapling_"..color, {
type = "fixed",
fixed = {-5 / 16, -0.5, -5 / 16, 5 / 16, 0.5, 5 / 16},
},
place_param2 = 1,
place_param2 = 0,
on_place = function(itemstack, placer, pointed_thing)
minetest.set_node(pointed_thing.above, {name="farming_super:orange_sapling_"..color, param2 = 1})
minetest.set_node(pointed_thing.above, {name="farming_super:orange_sapling", param2 = 0})
local timer = minetest.get_node_timer(pointed_thing.above)
timer:start(orange_speed.sapling + gr())
@ -144,33 +390,67 @@ minetest.register_node("farming_super:orange_sapling_"..color, {
end,
on_timer = function(pos, elapsed)
local node = minetest.get_node(pos)
local def = minetest.registered_nodes[node.name]
local c = def.orange_color
pos.y = pos.y - 1
local soil = minetest.get_node(pos)
if soil.name ~= "farming:desert_sand_soil_wet" then
pos.y = pos.y + 1
-- print("wrong soil")
minetest.get_node_timer(pos):start(orange_speed.retry)
return
end
pos.y = pos.y + 3
local wire = minetest.get_node(pos)
if wire.name ~= "farming_super:wire" then
pos.y = pos.y - 2
minetest.get_node_timer(pos):start(orange_speed.retry)
-- print("no wire")
return
end
pos.y = pos.y - 1
minetest.set_node(pos, {name = "farming_super:orange_leaves_"..color, param2 = 3})
minetest.get_node_timer(pos):start(orange_speed.fruit + gr())
pos.y = pos.y - 1
minetest.set_node(pos, {name = "farming_super:orange_stem_"..color, param2 = 1})
advance_trunk(pos, 0)
end,
})
]]
minetest.register_abm({
nodenames = {"farming_super:orange_seed"},
interval = 1,
chance = 3,
action = function(pos, node)
pos.y = pos.y - 1
local n = minetest.get_node(pos)
if n.name == "farming:soil_wet" then
pos.y = pos.y + 1
minetest.set_node(pos, {name="farming_super:orange_sapling"})
end
end,
})
minetest.register_abm({
nodenames = {"group:tree_trunk_root_fertile"},
interval = 30,
chance = 1,
action = function(pos, node)
local meta = minetest.get_meta(pos)
local stage = meta:get_int("stage")
if stage == 0 then stage = 1 end
local m = stage_data[stage]
local raw_leaves = meta:get_string("leaves")
local leaves = minetest.deserialize(raw_leaves)
if not leaves then
return
end
local raw_flowers = meta:get_string("flowers")
local flowers = minetest.deserialize(raw_flowers)
if not flowers then
flowers = {}
else
return -- don't re-flower, for debugging
end
for _,v in ipairs(leaves) do
if math.random() < 0.1 * stage then
local timer = minetest.get_node_timer(v)
if not timer:is_started() then
timer:start(leaf_times[1])
table.insert(flowers, v)
end
end
end
meta:set_string("flowers", minetest.serialize(flowers))
end,
})