Cleanup farming code and small additional changes

Some additional changes:
Hoes only work if the node is pointed to from above.
Hoe description, inventory_image and max_uses must be specified (when registering).
Nodes with the field group must have all soil values in the node definition.
Field nodes do not loose their param2 value (e.g. rotation) when they dry, get wet or get hoed.
The node above the hoed one is not checked for protection because that node is not changed; similarly, the node under a seed is not tested for protection.
Document the fertility
test for nil player in the hoe on_use function
properly test for the creative mod
ensure that the on_place function returns an itemstack
change missing soil fields message
This commit is contained in:
HybridDog 2016-05-23 13:10:16 +02:00
parent dd91a1bfe5
commit 4e8db84635
4 changed files with 204 additions and 213 deletions

View file

@ -347,13 +347,21 @@ The farming API allows you to easily register plants and hoes.
### Hoe Definition ### Hoe Definition
{ {
description = "", -- Description for tooltip -- Description for tooltip
inventory_image = "unknown_item.png", -- Image to be used as wield- and inventory image description = "My Hoe",
max_uses = 30, -- Uses until destroyed
material = "", -- Material for recipes -- Image to be used as wield- and inventory image
recipe = { -- Craft recipe, if material isn't used inventory_image = "unknown_item.png",
-- Uses until destroyed
max_uses = 30,
-- Material for recipes
material = "",
-- Craft recipe, if material isn't used
recipe = {
{"air", "air", "air"}, {"air", "air", "air"},
{"", "group:stick"}, {"", "group:stick"},
{"", "group:stick"}, {"", "group:stick"},
@ -363,14 +371,27 @@ The farming API allows you to easily register plants and hoes.
### Plant definition ### Plant definition
{ {
description = "", -- Description of seed item -- Description of seed item
harvest_description = "", -- Description of harvest item description = "My Plant",
-- (optional, derived automatically if not provided)
inventory_image = "unknown_item.png", -- Image to be used as seed's wield- and inventory image -- Description of harvest item (optional, derived automatically if not
steps = 8, -- How many steps the plant has to grow, until it can be harvested -- provided)
-- ^ Always provide a plant texture for each step, format: modname_plantname_i.png (i = stepnumber) harvest_description = "",
minlight = 13, -- Minimum light to grow
maxlight = default.LIGHT_MAX -- Maximum light to grow -- Image to be used as seed's wield- and inventory image
inventory_image = "unknown_item.png",
-- How many steps the plant has to grow, until it can be harvested
steps = 8,
-- ^ Always provide a plant texture for each step, format:
-- modname_plantname_i.png (i = stepnumber)
-- Groups of soil nodes on which the seed can grow
fertility = {"grassland"},
-- Minimum and maximum light to grow
minlight = 1,
maxlight = default.LIGHT_MAX
} }

View file

@ -1,73 +1,58 @@
-- farming/api.lua -- farming/api.lua
-- support for MT game translation.
local S = farming.get_translator
-- Wear out hoes, place soil -- Wear out hoes, place soil
-- TODO Ignore group:flower -- TODO Ignore group:flower
farming.registered_plants = {} farming.registered_plants = {}
farming.hoe_on_use = function(itemstack, user, pointed_thing, uses) function farming.hoe_on_use(itemstack, user, pt, uses)
local pt = pointed_thing if not pt or pt.type ~= "node" or pt.above.y ~= pt.under.y + 1 then
-- check if pointing at a node -- Only nodes pointed on the top can be hoed
if not pt then
return
end
if pt.type ~= "node" then
return return
end end
local under = minetest.get_node(pt.under) if minetest.get_node(pt.above).name ~= "air" then
local p = {x=pt.under.x, y=pt.under.y+1, z=pt.under.z} -- The hoe is obstructed from moving if there is no free space
local above = minetest.get_node(p)
-- return if any of the nodes is not registered
if not minetest.registered_nodes[under.name] then
return
end
if not minetest.registered_nodes[above.name] then
return return
end end
-- check if the node above the pointed thing is air local node_under = minetest.get_node(pt.under)
if above.name ~= "air" then local node_under_def = minetest.registered_nodes[node_under.name]
if not node_under_def or
minetest.get_item_group(node_under.name, "soil") ~= 1 then
-- Not a soil node
return return
end end
-- check if pointing at soil -- Test if soil properties are defined
if minetest.get_item_group(under.name, "soil") ~= 1 then local soil = node_under_def.soil
if not soil or not soil.wet or not soil.dry then
return return
end end
-- check if (wet) soil defined local playername = user and user:get_player_name() or ""
local regN = minetest.registered_nodes if minetest.is_protected(pt.under, playername) then
if regN[under.name].soil == nil or regN[under.name].soil.wet == nil or regN[under.name].soil.dry == nil then minetest.record_protection_violation(pt.under, playername)
return return
end end
if minetest.is_protected(pt.under, user:get_player_name()) then -- Put the node which should appear after applying the hoe
minetest.record_protection_violation(pt.under, user:get_player_name()) node_under.name = node_under_def.soil.dry
return minetest.swap_node(pt.under, node_under)
end
if minetest.is_protected(pt.above, user:get_player_name()) then
minetest.record_protection_violation(pt.above, user:get_player_name())
return
end
-- turn the node into soil and play sound
minetest.set_node(pt.under, {name = regN[under.name].soil.dry})
minetest.sound_play("default_dig_crumbly", { minetest.sound_play("default_dig_crumbly", {
pos = pt.under, pos = pt.under,
gain = 0.5, gain = 0.5,
}, true) }, true)
if not (creative and creative.is_enabled_for if minetest.global_exists("creative")
and creative.is_enabled_for(user:get_player_name())) then and creative.is_enabled_for(playername) then
-- wear tool return
end
-- wear tool
itemstack:add_wear(65535 / (uses - 1))
if itemstack:is_empty() then
local wdef = itemstack:get_definition() local wdef = itemstack:get_definition()
itemstack:add_wear(65535/(uses-1)) if wdef.sound and wdef.sound.breaks then
-- tool break sound
if itemstack:get_count() == 0 and wdef.sound and wdef.sound.breaks then
minetest.sound_play(wdef.sound.breaks, {pos = pt.above, minetest.sound_play(wdef.sound.breaks, {pos = pt.above,
gain = 0.5}, true) gain = 0.5}, true)
end end
@ -76,31 +61,29 @@ farming.hoe_on_use = function(itemstack, user, pointed_thing, uses)
end end
-- Register new hoes -- Register new hoes
farming.register_hoe = function(name, def) function farming.register_hoe(name, def)
-- Check for : prefix (register new hoes in your mod's namespace) -- Check for : prefix (register new hoes in your mod's namespace)
if name:sub(1,1) ~= ":" then if name:sub(1,1) ~= ":" then
name = ":" .. name name = ":" .. name
end end
-- Check def table -- Check def table
if def.description == nil then assert(def.description, "Missing hoe description for " .. name)
def.description = S("Hoe") assert(def.inventory_image, "Missing inventory image for " .. name)
end assert(def.max_uses and def.max_uses > 1,
if def.inventory_image == nil then "max_uses are invalid (hoe " .. name .. ")")
def.inventory_image = "unknown_item.png"
end
if def.max_uses == nil then
def.max_uses = 30
end
-- Register the tool -- Register the tool
minetest.register_tool(name, { minetest.register_tool(name, {
description = def.description, description = def.description,
inventory_image = def.inventory_image, inventory_image = def.inventory_image,
on_use = function(itemstack, user, pointed_thing) on_use = function(itemstack, user, pointed_thing)
return farming.hoe_on_use(itemstack, user, pointed_thing, def.max_uses) return farming.hoe_on_use(itemstack, user, pointed_thing,
def.max_uses)
end, end,
groups = def.groups, groups = def.groups,
sound = {breaks = "default_tool_breaks"}, sound = {breaks = "default_tool_breaks"},
}) })
-- Register its recipe -- Register its recipe
if def.recipe then if def.recipe then
minetest.register_craft({ minetest.register_craft({
@ -129,62 +112,43 @@ local function tick_again(pos)
end end
-- Seed placement -- Seed placement
farming.place_seed = function(itemstack, placer, pointed_thing, plantname) function farming.place_seed(itemstack, placer, pt, plantname)
local pt = pointed_thing if not pt or pt.type ~= "node" or pt.above.y ~= pt.under.y + 1 then
-- check if pointing at a node -- Seeds can only be placed on top of a node
if not pt then
return itemstack
end
if pt.type ~= "node" then
return itemstack
end
local under = minetest.get_node(pt.under)
local above = minetest.get_node(pt.above)
local player_name = placer and placer:get_player_name() or ""
if minetest.is_protected(pt.under, player_name) then
minetest.record_protection_violation(pt.under, player_name)
return
end
if minetest.is_protected(pt.above, player_name) then
minetest.record_protection_violation(pt.above, player_name)
return return
end end
-- return if any of the nodes is not registered local playername = placer and placer:get_player_name() or ""
if not minetest.registered_nodes[under.name] then if minetest.is_protected(pt.above, playername) then
return itemstack minetest.record_protection_violation(pt.above, playername)
end return
if not minetest.registered_nodes[above.name] then
return itemstack
end end
-- check if pointing at the top of the node local node_above_def = minetest.registered_nodes[
if pt.above.y ~= pt.under.y+1 then minetest.get_node(pt.above).name]
return itemstack if not node_above_def or not node_above_def.buildable_to then
-- We cannot put the seed here
return
end end
-- check if you can replace the node above the pointed node -- The seed must be placed onto a soil node
if not minetest.registered_nodes[above.name].buildable_to then local node_under = minetest.get_node(pt.under)
return itemstack if minetest.get_item_group(node_under.name, "soil") < 2 then
return
end end
-- check if pointing at soil -- Put the seed node
if minetest.get_item_group(under.name, "soil") < 2 then minetest.log("action", playername .. " places node " .. plantname ..
return itemstack " at " .. minetest.pos_to_string(pt.above))
end
-- add the node and remove 1 item from the itemstack
minetest.log("action", player_name .. " places node " .. plantname .. " at " ..
minetest.pos_to_string(pt.above))
minetest.add_node(pt.above, {name = plantname, param2 = 1}) minetest.add_node(pt.above, {name = plantname, param2 = 1})
tick(pt.above) tick(pt.above)
if not (creative and creative.is_enabled_for
and creative.is_enabled_for(player_name)) then if minetest.global_exists("creative")
itemstack:take_item() and creative.is_enabled_for(playername) then
return
end end
itemstack:take_item()
return itemstack return itemstack
end end
@ -200,14 +164,15 @@ farming.grow_plant = function(pos, elapsed)
-- grow seed -- grow seed
if minetest.get_item_group(node.name, "seed") and def.fertility then if minetest.get_item_group(node.name, "seed") and def.fertility then
local soil_node = minetest.get_node_or_nil({x = pos.x, y = pos.y - 1, z = pos.z}) local soil_node = minetest.get_node_or_nil(
{x = pos.x, y = pos.y - 1, z = pos.z})
if not soil_node then if not soil_node then
tick_again(pos) tick_again(pos)
return return
end end
-- omitted is a check for light, we assume seeds can germinate in the dark. -- omitted is a check for light, we assume seeds can germinate in the dark.
for _, v in pairs(def.fertility) do for _, groupname in ipairs(def.fertility) do
if minetest.get_item_group(soil_node.name, v) ~= 0 then if minetest.get_item_group(soil_node.name, groupname) ~= 0 then
local placenode = {name = def.next_plant} local placenode = {name = def.next_plant}
if def.place_param2 then if def.place_param2 then
placenode.param2 = def.place_param2 placenode.param2 = def.place_param2
@ -252,48 +217,36 @@ farming.grow_plant = function(pos, elapsed)
end end
-- Register plants -- Register plants
farming.register_plant = function(name, def) function farming.register_plant(name, def)
local mname = name:split(":")[1] local mname, pname = unpack(name:split(":"))
local pname = name:split(":")[2]
-- Check def table -- Check def table
if not def.description then
def.description = S("Seed")
end
if not def.harvest_description then if not def.harvest_description then
def.harvest_description = pname:gsub("^%l", string.upper) def.harvest_description = pname:gsub("^%l", string.upper)
end end
if not def.inventory_image then assert(def.description, "Missing description for " .. name)
def.inventory_image = "unknown_item.png" assert(def.inventory_image, "Missing inventory_image for " .. name)
end assert(def.steps, "Missing number of steps for " .. name)
if not def.steps then assert(def.fertility and def.fertility[1], "Missing fertility for " .. name)
return nil def.minlight = def.minlight or 1
end def.maxlight = def.maxlight or default.LIGHT_MAX
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
farming.registered_plants[pname] = def farming.registered_plants[pname] = def
-- Register seed -- Register seed
local lbm_nodes = {mname .. ":seed_" .. pname} local lbm_nodes = {mname .. ":seed_" .. pname}
local g = {seed = 1, snappy = 3, attached_node = 1, flammable = 2} local seed_groups = {seed = 1, snappy = 3, attached_node = 1, flammable = 2}
for k, v in pairs(def.fertility) do for _, groupname in ipairs(def.fertility) do
g[v] = 1 seed_groups[groupname] = 1
end end
minetest.register_node(":" .. mname .. ":seed_" .. pname, { minetest.register_node(":" .. mname .. ":seed_" .. pname, {
description = def.description, description = def.description,
tiles = {def.inventory_image}, tiles = {def.inventory_image},
inventory_image = def.inventory_image, inventory_image = def.inventory_image,
wield_image = def.inventory_image, wield_image = def.inventory_image,
drawtype = "signlike", drawtype = "signlike",
groups = g, groups = seed_groups,
paramtype = "light", paramtype = "light",
paramtype2 = "wallmounted", paramtype2 = "wallmounted",
place_param2 = def.place_param2 or nil, -- this isn't actually used for placement place_param2 = def.place_param2 or nil, -- this isn't actually used for placement
@ -321,7 +274,8 @@ farming.register_plant = function(name, def)
pointed_thing) or itemstack pointed_thing) or itemstack
end end
return farming.place_seed(itemstack, placer, pointed_thing, mname .. ":seed_" .. pname) return farming.place_seed(itemstack, placer, pointed_thing,
mname .. ":seed_" .. pname) or itemstack
end, end,
next_plant = mname .. ":" .. pname .. "_1", next_plant = mname .. ":" .. pname .. "_1",
on_timer = farming.grow_plant, on_timer = farming.grow_plant,
@ -350,8 +304,6 @@ farming.register_plant = function(name, def)
{items = {mname .. ":seed_" .. pname}, rarity = base_rarity * 2}, {items = {mname .. ":seed_" .. pname}, rarity = base_rarity * 2},
} }
} }
local nodegroups = {snappy = 3, flammable = 2, plant = 1, not_in_creative_inventory = 1, attached_node = 1}
nodegroups[pname] = i
local next_plant = nil local next_plant = nil
@ -374,7 +326,8 @@ farming.register_plant = function(name, def)
type = "fixed", type = "fixed",
fixed = {-0.5, -0.5, -0.5, 0.5, -5/16, 0.5}, fixed = {-0.5, -0.5, -0.5, 0.5, -5/16, 0.5},
}, },
groups = nodegroups, groups = {snappy = 3, flammable = 2, plant = 1,
not_in_creative_inventory = 1, attached_node = 1, [pname] = i},
sounds = default.node_sound_leaves_defaults(), sounds = default.node_sound_leaves_defaults(),
next_plant = next_plant, next_plant = next_plant,
on_timer = farming.grow_plant, on_timer = farming.grow_plant,
@ -387,15 +340,12 @@ farming.register_plant = function(name, def)
minetest.register_lbm({ minetest.register_lbm({
name = ":" .. mname .. ":start_nodetimer_" .. pname, name = ":" .. mname .. ":start_nodetimer_" .. pname,
nodenames = lbm_nodes, nodenames = lbm_nodes,
action = function(pos, node) action = tick_again,
tick_again(pos)
end,
}) })
-- Return -- Return
local r = { return {
seed = mname .. ":seed_" .. pname, seed = mname .. ":seed_" .. pname,
harvest = mname .. ":" .. pname harvest = mname .. ":" .. pname
} }
return r
end end

View file

@ -1,4 +1,4 @@
name = farming name = farming
description = Minetest Game mod: farming description = Minetest Game mod: farming
depends = default, wool, stairs depends = default, wool, stairs
optional_depends = dungeon_loot optional_depends = dungeon_loot, creative

View file

@ -63,7 +63,8 @@ minetest.register_node("farming:soil", {
description = S("Soil"), description = S("Soil"),
tiles = {"default_dirt.png^farming_soil.png", "default_dirt.png"}, tiles = {"default_dirt.png^farming_soil.png", "default_dirt.png"},
drop = "default:dirt", drop = "default:dirt",
groups = {crumbly=3, not_in_creative_inventory=1, soil=2, grassland = 1, field = 1}, groups = {crumbly = 3, not_in_creative_inventory = 1, soil = 2,
grassland = 1, field = 1},
sounds = default.node_sound_dirt_defaults(), sounds = default.node_sound_dirt_defaults(),
soil = { soil = {
base = "default:dirt", base = "default:dirt",
@ -74,9 +75,11 @@ minetest.register_node("farming:soil", {
minetest.register_node("farming:soil_wet", { minetest.register_node("farming:soil_wet", {
description = S("Wet Soil"), description = S("Wet Soil"),
tiles = {"default_dirt.png^farming_soil_wet.png", "default_dirt.png^farming_soil_wet_side.png"}, tiles = {"default_dirt.png^farming_soil_wet.png",
"default_dirt.png^farming_soil_wet_side.png"},
drop = "default:dirt", drop = "default:dirt",
groups = {crumbly=3, not_in_creative_inventory=1, soil=3, wet = 1, grassland = 1, field = 1}, groups = {crumbly = 3, not_in_creative_inventory = 1, soil = 3, wet = 1,
grassland = 1, field = 1},
sounds = default.node_sound_dirt_defaults(), sounds = default.node_sound_dirt_defaults(),
soil = { soil = {
base = "default:dirt", base = "default:dirt",
@ -89,7 +92,8 @@ minetest.register_node("farming:dry_soil", {
description = S("Savanna Soil"), description = S("Savanna Soil"),
tiles = {"default_dry_dirt.png^farming_soil.png", "default_dry_dirt.png"}, tiles = {"default_dry_dirt.png^farming_soil.png", "default_dry_dirt.png"},
drop = "default:dry_dirt", drop = "default:dry_dirt",
groups = {crumbly=3, not_in_creative_inventory=1, soil=2, grassland = 1, field = 1}, groups = {crumbly=3, not_in_creative_inventory=1, soil=2, grassland = 1,
field = 1},
sounds = default.node_sound_dirt_defaults(), sounds = default.node_sound_dirt_defaults(),
soil = { soil = {
base = "default:dry_dirt", base = "default:dry_dirt",
@ -100,9 +104,11 @@ minetest.register_node("farming:dry_soil", {
minetest.register_node("farming:dry_soil_wet", { minetest.register_node("farming:dry_soil_wet", {
description = S("Wet Savanna Soil"), description = S("Wet Savanna Soil"),
tiles = {"default_dry_dirt.png^farming_soil_wet.png", "default_dry_dirt.png^farming_soil_wet_side.png"}, tiles = {"default_dry_dirt.png^farming_soil_wet.png",
"default_dry_dirt.png^farming_soil_wet_side.png"},
drop = "default:dry_dirt", drop = "default:dry_dirt",
groups = {crumbly=3, not_in_creative_inventory=1, soil=3, wet = 1, grassland = 1, field = 1}, groups = {crumbly=3, not_in_creative_inventory=1, soil=3, wet = 1,
grassland = 1, field = 1},
sounds = default.node_sound_dirt_defaults(), sounds = default.node_sound_dirt_defaults(),
soil = { soil = {
base = "default:dry_dirt", base = "default:dry_dirt",
@ -123,7 +129,8 @@ minetest.register_node("farming:desert_sand_soil", {
description = S("Desert Sand Soil"), description = S("Desert Sand Soil"),
drop = "default:desert_sand", drop = "default:desert_sand",
tiles = {"farming_desert_sand_soil.png", "default_desert_sand.png"}, tiles = {"farming_desert_sand_soil.png", "default_desert_sand.png"},
groups = {crumbly=3, not_in_creative_inventory = 1, falling_node=1, sand=1, soil = 2, desert = 1, field = 1}, groups = {crumbly = 3, not_in_creative_inventory = 1, falling_node = 1,
sand = 1, soil = 2, desert = 1, field = 1},
sounds = default.node_sound_sand_defaults(), sounds = default.node_sound_sand_defaults(),
soil = { soil = {
base = "default:desert_sand", base = "default:desert_sand",
@ -135,8 +142,10 @@ minetest.register_node("farming:desert_sand_soil", {
minetest.register_node("farming:desert_sand_soil_wet", { minetest.register_node("farming:desert_sand_soil_wet", {
description = S("Wet Desert Sand Soil"), description = S("Wet Desert Sand Soil"),
drop = "default:desert_sand", drop = "default:desert_sand",
tiles = {"farming_desert_sand_soil_wet.png", "farming_desert_sand_soil_wet_side.png"}, tiles = {"farming_desert_sand_soil_wet.png",
groups = {crumbly=3, falling_node=1, sand=1, not_in_creative_inventory=1, soil=3, wet = 1, desert = 1, field = 1}, "farming_desert_sand_soil_wet_side.png"},
groups = {crumbly = 3, falling_node = 1, sand = 1, desert = 1,
not_in_creative_inventory = 1, soil = 3, wet = 1, field = 1},
sounds = default.node_sound_sand_defaults(), sounds = default.node_sound_sand_defaults(),
soil = { soil = {
base = "default:desert_sand", base = "default:desert_sand",
@ -182,49 +191,56 @@ minetest.register_abm({
interval = 15, interval = 15,
chance = 4, chance = 4,
action = function(pos, node) action = function(pos, node)
local n_def = minetest.registered_nodes[node.name] or nil
local wet = n_def.soil.wet or nil
local base = n_def.soil.base or nil
local dry = n_def.soil.dry or nil
if not n_def or not n_def.soil or not wet or not base or not dry then
return
end
pos.y = pos.y + 1 pos.y = pos.y + 1
local nn = minetest.get_node_or_nil(pos) local nn = minetest.get_node_or_nil(pos)
if not nn or not nn.name then if not nn then
return return
end end
local nn_def = minetest.registered_nodes[nn.name] or nil local nn_def = minetest.registered_nodes[nn.name]
pos.y = pos.y - 1 pos.y = pos.y - 1
if nn_def and nn_def.walkable and minetest.get_item_group(nn.name, "plant") == 0 then local soil = minetest.registered_nodes[node.name].soil
minetest.set_node(pos, {name = base}) assert(soil and soil.wet and soil.base and soil.dry,
"Field node " .. node.name .. " lacks of either 'wet', 'base' " ..
"or 'dry' properties.")
if nn_def and nn_def.walkable and
minetest.get_item_group(nn.name, "plant") == 0 then
node.name = soil.base
minetest.set_node(pos, node)
return return
end end
-- check if there is water nearby
local wet_lvl = minetest.get_item_group(node.name, "wet")
if minetest.find_node_near(pos, 3, {"group:water"}) then
-- if it is dry soil and not base node, turn it into wet soil
if wet_lvl == 0 then
minetest.set_node(pos, {name = wet})
end
else
-- only turn back if there are no unloaded blocks (and therefore
-- possible water sources) nearby
if not minetest.find_node_near(pos, 3, {"ignore"}) then
-- turn it back into base if it is already dry
if wet_lvl == 0 then
-- only turn it back if there is no plant/seed on top of it
if minetest.get_item_group(nn.name, "plant") == 0 and minetest.get_item_group(nn.name, "seed") == 0 then
minetest.set_node(pos, {name = base})
end
-- if its wet turn it back into dry soil local wet_lvl = minetest.get_item_group(node.name, "wet")
elseif wet_lvl == 1 then -- Make the node wet if water is near it
minetest.set_node(pos, {name = dry}) if minetest.find_node_near(pos, 3, {"group:water"}) then
end -- If it is dry soil and not base node, turn it into wet soil
if wet_lvl == 0 then
node.name = soil.wet
minetest.set_node(pos, node)
end end
return
end
-- Only dry out if there are no unloaded blocks (and therefore
-- possible water sources) nearby
if minetest.find_node_near(pos, 3, {"ignore"}) then
return
end
-- Turn it back into base if it is already dry and no plant/seed
-- is on top of it
if wet_lvl == 0 then
if minetest.get_item_group(nn.name, "plant") == 0 and
minetest.get_item_group(nn.name, "seed") == 0 then
node.name = soil.base
minetest.set_node(pos, node)
end
-- If it is wet turn it back into dry soil
elseif wet_lvl == 1 then
node.name = soil.dry
minetest.set_node(pos, node)
end end
end, end,
}) })
@ -233,13 +249,15 @@ minetest.register_abm({
-- Make default:grass_* occasionally drop wheat seed -- Make default:grass_* occasionally drop wheat seed
for i = 1, 5 do for i = 1, 5 do
minetest.override_item("default:grass_"..i, {drop = { minetest.override_item("default:grass_" .. i, {
max_items = 1, drop = {
items = { max_items = 1,
{items = {"farming:seed_wheat"}, rarity = 5}, items = {
{items = {"default:grass_1"}}, {items = {"farming:seed_wheat"}, rarity = 5},
{items = {"default:grass_1"}},
}
} }
}}) })
end end
@ -250,13 +268,15 @@ end
-- This source is kept for now to avoid disruption but should probably be -- This source is kept for now to avoid disruption but should probably be
-- removed in future as players get used to the new source. -- removed in future as players get used to the new source.
minetest.override_item("default:junglegrass", {drop = { minetest.override_item("default:junglegrass", {
max_items = 1, drop = {
items = { max_items = 1,
{items = {"farming:seed_cotton"}, rarity = 8}, items = {
{items = {"default:junglegrass"}}, {items = {"farming:seed_cotton"}, rarity = 8},
{items = {"default:junglegrass"}},
}
} }
}}) })
-- Wild cotton as a source of cotton seed -- Wild cotton as a source of cotton seed