]> git.lizzy.rs Git - Crafter.git/commitdiff
Add furnace
authorOilboi <oil.boi.minetest@gmail.com>
Thu, 13 Feb 2020 06:51:40 +0000 (01:51 -0500)
committerOilboi <oil.boi.minetest@gmail.com>
Thu, 13 Feb 2020 06:51:40 +0000 (01:51 -0500)
14 files changed:
mods/main/craft_recipes.lua
mods/main/textures/default_furnace_fire_bg.png [new file with mode: 0755]
mods/main/textures/default_furnace_fire_fg.png [new file with mode: 0755]
mods/main/textures/furnace_bottom.png [new file with mode: 0755]
mods/main/textures/furnace_front.png [new file with mode: 0755]
mods/main/textures/furnace_front_active.png [new file with mode: 0755]
mods/main/textures/furnace_side.png [new file with mode: 0755]
mods/main/textures/furnace_top.png [new file with mode: 0755]
mods/main/textures/gui_furnace_arrow_bg.png [new file with mode: 0755]
mods/main/textures/gui_furnace_arrow_fg.png [new file with mode: 0755]
mods/main/textures/gui_hb_bg.png [new file with mode: 0755]
mods/utility/depends.txt [new file with mode: 0644]
mods/utility/init.lua [new file with mode: 0644]
todo.txt

index 0c71e1e9c44e477b87474ce7272e267130fab0a1..c679d3b7abb6fb9c7b37545b2f70142acda53843 100644 (file)
@@ -1,8 +1,49 @@
 --crafting recipes
-local tool =     {"wood","stone", "iron","gold","diamond"}--the tool name
-local material = {"wood","cobble","iron","gold","diamond"}--material to craft
 
+--cooking
+minetest.register_craft({
+       type = "cooking",
+       output = "main:diamond",
+       recipe = "main:diamondore",
+})
+minetest.register_craft({
+       type = "cooking",
+       output = "main:coal 4",
+       recipe = "main:coalore",
+})
+minetest.register_craft({
+       type = "cooking",
+       output = "main:gold",
+       recipe = "main:goldore",
+})
+minetest.register_craft({
+       type = "cooking",
+       output = "main:iron",
+       recipe = "main:ironore",
+})
+--fuel
+minetest.register_craft({
+       type = "fuel",
+       recipe = "main:stick",
+       burntime = 3,
+})
 
+minetest.register_craft({
+       type = "fuel",
+       recipe = "main:wood",
+       burntime = 12,
+})
+minetest.register_craft({
+       type = "fuel",
+       recipe = "main:leaves",
+       burntime = 3,
+})
+minetest.register_craft({
+       type = "fuel",
+       recipe = "main:coal",
+       burntime = 20,
+})
+---crafting
 minetest.register_craft({
        type = "shapeless",
        output = "main:wood 4",
@@ -17,6 +58,8 @@ minetest.register_craft({
        }
 })
 
+local tool =     {"wood","stone", "iron","gold","diamond"}--the tool name
+local material = {"wood","cobble","iron","gold","diamond"}--material to craft
 
 for id,tool in pairs(tool) do
        minetest.register_craft({
diff --git a/mods/main/textures/default_furnace_fire_bg.png b/mods/main/textures/default_furnace_fire_bg.png
new file mode 100755 (executable)
index 0000000..abeefc0
Binary files /dev/null and b/mods/main/textures/default_furnace_fire_bg.png differ
diff --git a/mods/main/textures/default_furnace_fire_fg.png b/mods/main/textures/default_furnace_fire_fg.png
new file mode 100755 (executable)
index 0000000..e5b3909
Binary files /dev/null and b/mods/main/textures/default_furnace_fire_fg.png differ
diff --git a/mods/main/textures/furnace_bottom.png b/mods/main/textures/furnace_bottom.png
new file mode 100755 (executable)
index 0000000..7844072
Binary files /dev/null and b/mods/main/textures/furnace_bottom.png differ
diff --git a/mods/main/textures/furnace_front.png b/mods/main/textures/furnace_front.png
new file mode 100755 (executable)
index 0000000..388addd
Binary files /dev/null and b/mods/main/textures/furnace_front.png differ
diff --git a/mods/main/textures/furnace_front_active.png b/mods/main/textures/furnace_front_active.png
new file mode 100755 (executable)
index 0000000..c425604
Binary files /dev/null and b/mods/main/textures/furnace_front_active.png differ
diff --git a/mods/main/textures/furnace_side.png b/mods/main/textures/furnace_side.png
new file mode 100755 (executable)
index 0000000..c154414
Binary files /dev/null and b/mods/main/textures/furnace_side.png differ
diff --git a/mods/main/textures/furnace_top.png b/mods/main/textures/furnace_top.png
new file mode 100755 (executable)
index 0000000..7844072
Binary files /dev/null and b/mods/main/textures/furnace_top.png differ
diff --git a/mods/main/textures/gui_furnace_arrow_bg.png b/mods/main/textures/gui_furnace_arrow_bg.png
new file mode 100755 (executable)
index 0000000..2456a80
Binary files /dev/null and b/mods/main/textures/gui_furnace_arrow_bg.png differ
diff --git a/mods/main/textures/gui_furnace_arrow_fg.png b/mods/main/textures/gui_furnace_arrow_fg.png
new file mode 100755 (executable)
index 0000000..e140705
Binary files /dev/null and b/mods/main/textures/gui_furnace_arrow_fg.png differ
diff --git a/mods/main/textures/gui_hb_bg.png b/mods/main/textures/gui_hb_bg.png
new file mode 100755 (executable)
index 0000000..688ae6e
Binary files /dev/null and b/mods/main/textures/gui_hb_bg.png differ
diff --git a/mods/utility/depends.txt b/mods/utility/depends.txt
new file mode 100644 (file)
index 0000000..ba2906d
--- /dev/null
@@ -0,0 +1 @@
+main
diff --git a/mods/utility/init.lua b/mods/utility/init.lua
new file mode 100644 (file)
index 0000000..da9a95d
--- /dev/null
@@ -0,0 +1,378 @@
+--formspecs
+
+local furnace = {}
+
+function furnace.get_hotbar_bg(x,y)
+       local out = ""
+       for i=0,7,1 do
+               out = out .."image["..x+i..","..y..";1,1;gui_furnace_arrow_bg.png]"
+       end
+       return(out)
+end
+
+function furnace.get_inventory_drops(pos, inventory, drops)
+       local inv = minetest.get_meta(pos):get_inventory()
+       local n = #drops
+       for i = 1, inv:get_size(inventory) do
+               local stack = inv:get_stack(inventory, i)
+               if stack:get_count() > 0 then
+                       drops[n+1] = stack:to_table()
+                       n = n + 1
+               end
+       end
+end
+
+function furnace.get_furnace_active_formspec(fuel_percent, item_percent)
+       return "size[8,8.5]"..
+               "list[context;src;2.75,0.5;1,1;]"..
+               "list[context;fuel;2.75,2.5;1,1;]"..
+               "image[2.75,1.5;1,1;default_furnace_fire_bg.png^[lowpart:"..
+               (fuel_percent)..":default_furnace_fire_fg.png]"..
+               "image[3.75,1.5;1,1;gui_furnace_arrow_bg.png^[lowpart:"..
+               (item_percent)..":gui_furnace_arrow_fg.png^[transformR270]"..
+               "list[context;dst;4.75,0.96;2,2;]"..
+               "list[current_player;main;0,4.25;8,1;]"..
+               "list[current_player;main;0,5.5;8,3;8]"..
+               "listring[context;dst]"..
+               "listring[current_player;main]"..
+               "listring[context;src]"..
+               "listring[current_player;main]"..
+               "listring[context;fuel]"..
+               "listring[current_player;main]"..
+               furnace.get_hotbar_bg(0, 4.25)
+end
+
+function furnace.get_furnace_inactive_formspec()
+       return "size[8,8.5]"..
+               "list[context;src;2.75,0.5;1,1;]"..
+               "list[context;fuel;2.75,2.5;1,1;]"..
+               "image[2.75,1.5;1,1;default_furnace_fire_bg.png]"..
+               "image[3.75,1.5;1,1;gui_furnace_arrow_bg.png^[transformR270]"..
+               "list[context;dst;4.75,0.96;2,2;]"..
+               "list[current_player;main;0,4.25;8,1;]"..
+               "list[current_player;main;0,5.5;8,3;8]"..
+               "listring[context;dst]"..
+               "listring[current_player;main]"..
+               "listring[context;src]"..
+               "listring[current_player;main]"..
+               "listring[context;fuel]"..
+               "listring[current_player;main]"..
+               furnace.get_hotbar_bg(0, 4.25)
+end
+
+--
+-- Node callback functions that are the same for active and inactive furnace
+--
+
+local function can_dig(pos, player)
+       local meta = minetest.get_meta(pos);
+       local inv = meta:get_inventory()
+       return inv:is_empty("fuel") and inv:is_empty("dst") and inv:is_empty("src")
+end
+
+local function allow_metadata_inventory_put(pos, listname, index, stack, player)
+       if minetest.is_protected(pos, player:get_player_name()) then
+               return 0
+       end
+       local meta = minetest.get_meta(pos)
+       local inv = meta:get_inventory()
+       if listname == "fuel" then
+               if minetest.get_craft_result({method="fuel", width=1, items={stack}}).time ~= 0 then
+                       if inv:is_empty("src") then
+                               meta:set_string("infotext", "Furnace is empty")
+                       end
+                       return stack:get_count()
+               else
+                       return 0
+               end
+       elseif listname == "src" then
+               return stack:get_count()
+       elseif listname == "dst" then
+               return 0
+       end
+end
+
+local function allow_metadata_inventory_move(pos, from_list, from_index, to_list, to_index, count, player)
+       local meta = minetest.get_meta(pos)
+       local inv = meta:get_inventory()
+       local stack = inv:get_stack(from_list, from_index)
+       return allow_metadata_inventory_put(pos, to_list, to_index, stack, player)
+end
+
+local function allow_metadata_inventory_take(pos, listname, index, stack, player)
+       if minetest.is_protected(pos, player:get_player_name()) then
+               return 0
+       end
+       return stack:get_count()
+end
+
+local function swap_node(pos, name)
+       local node = minetest.get_node(pos)
+       if node.name == name then
+               return
+       end
+       node.name = name
+       minetest.swap_node(pos, node)
+end
+
+local function furnace_node_timer(pos, elapsed)
+       --
+       -- Initialize metadata
+       --
+       local meta = minetest.get_meta(pos)
+       local fuel_time = meta:get_float("fuel_time") or 0
+       local src_time = meta:get_float("src_time") or 0
+       local fuel_totaltime = meta:get_float("fuel_totaltime") or 0
+
+       local inv = meta:get_inventory()
+       local srclist, fuellist
+       local dst_full = false
+
+       local cookable, cooked
+       local fuel
+
+       local update = true
+       while elapsed > 0 and update do
+               update = false
+
+               srclist = inv:get_list("src")
+               fuellist = inv:get_list("fuel")
+
+               --
+               -- Cooking
+               --
+
+               -- Check if we have cookable content
+               local aftercooked
+               cooked, aftercooked = minetest.get_craft_result({method = "cooking", width = 1, items = srclist})
+               cookable = cooked.time ~= 0
+
+               local el = math.min(elapsed, fuel_totaltime - fuel_time)
+               if cookable then -- fuel lasts long enough, adjust el to cooking duration
+                       el = math.min(el, cooked.time - src_time)
+               end
+
+               -- Check if we have enough fuel to burn
+               if fuel_time < fuel_totaltime then
+                       -- The furnace is currently active and has enough fuel
+                       fuel_time = fuel_time + el
+                       -- If there is a cookable item then check if it is ready yet
+                       if cookable then
+                               src_time = src_time + el
+                               if src_time >= cooked.time then
+                                       -- Place result in dst list if possible
+                                       if inv:room_for_item("dst", cooked.item) then
+                                               inv:add_item("dst", cooked.item)
+                                               inv:set_stack("src", 1, aftercooked.items[1])
+                                               src_time = src_time - cooked.time
+                                               update = true
+                                       else
+                                               dst_full = true
+                                       end
+                               else
+                                       -- Item could not be cooked: probably missing fuel
+                                       update = true
+                               end
+                       end
+               else
+                       -- Furnace ran out of fuel
+                       if cookable then
+                               -- We need to get new fuel
+                               local afterfuel
+                               fuel, afterfuel = minetest.get_craft_result({method = "fuel", width = 1, items = fuellist})
+
+                               if fuel.time == 0 then
+                                       -- No valid fuel in fuel list
+                                       fuel_totaltime = 0
+                                       src_time = 0
+                               else
+                                       -- Take fuel from fuel list
+                                       inv:set_stack("fuel", 1, afterfuel.items[1])
+                                       -- Put replacements in dst list or drop them on the furnace.
+                                       local replacements = fuel.replacements
+                                       if replacements[1] then
+                                               local leftover = inv:add_item("dst", replacements[1])
+                                               if not leftover:is_empty() then
+                                                       local above = vector.new(pos.x, pos.y + 1, pos.z)
+                                                       local drop_pos = minetest.find_node_near(above, 1, {"air"}) or above
+                                                       minetest.item_drop(replacements[1], nil, drop_pos)
+                                               end
+                                       end
+                                       update = true
+                                       fuel_totaltime = fuel.time + (fuel_totaltime - fuel_time)
+                               end
+                       else
+                               -- We don't need to get new fuel since there is no cookable item
+                               fuel_totaltime = 0
+                               src_time = 0
+                       end
+                       fuel_time = 0
+               end
+
+               elapsed = elapsed - el
+       end
+
+       if fuel and fuel_totaltime > fuel.time then
+               fuel_totaltime = fuel.time
+       end
+       if srclist and srclist[1]:is_empty() then
+               src_time = 0
+       end
+
+       --
+       -- Update formspec, infotext and node
+       --
+       local formspec
+       local item_state
+       local item_percent = 0
+       if cookable then
+               item_percent = math.floor(src_time / cooked.time * 100)
+               if dst_full then
+                       item_state = "100% (output full)"
+               else
+                       item_state = "@1%", item_percent
+               end
+       else
+               if srclist and not srclist[1]:is_empty() then
+                       item_state = "Not cookable"
+               else
+                       item_state = "Empty"
+               end
+       end
+
+       local fuel_state = "Empty"
+       local active = false
+       local result = false
+
+       if fuel_totaltime ~= 0 then
+               active = true
+               local fuel_percent = 100 - math.floor(fuel_time / fuel_totaltime * 100)
+               fuel_state = "@1%", fuel_percent
+               formspec = furnace.get_furnace_active_formspec(fuel_percent, item_percent)
+               swap_node(pos, "utility:furnace_active")
+               -- make sure timer restarts automatically
+               result = true
+       else
+               if fuellist and not fuellist[1]:is_empty() then
+                       fuel_state = "@1%", 0
+               end
+               formspec = furnace.get_furnace_inactive_formspec()
+               swap_node(pos, "utility:furnace")
+               -- stop timer on the inactive furnace
+               minetest.get_node_timer(pos):stop()
+       end
+
+
+       local infotext
+       if active then
+               infotext = "Furnace active"
+       else
+               infotext = "Furnace inactive"
+       end
+       infotext = infotext .. "\n" .. "(Item: @1; Fuel: @2)", item_state, fuel_state
+
+       --
+       -- Set meta values
+       --
+       meta:set_float("fuel_totaltime", fuel_totaltime)
+       meta:set_float("fuel_time", fuel_time)
+       meta:set_float("src_time", src_time)
+       meta:set_string("formspec", formspec)
+       meta:set_string("infotext", infotext)
+
+       return result
+end
+
+--
+-- Node definitions
+--
+
+minetest.register_node("utility:furnace", {
+       description = "Furnace",
+       tiles = {
+               "furnace_top.png", "furnace_bottom.png",
+               "furnace_side.png", "furnace_side.png",
+               "furnace_side.png", "furnace_front.png"
+       },
+       paramtype2 = "facedir",
+       groups = {stone=2},
+       legacy_facedir_simple = true,
+       is_ground_content = false,
+       sounds = main.stoneSound(),
+
+       can_dig = can_dig,
+
+       on_timer = furnace_node_timer,
+
+       on_construct = function(pos)
+               local meta = minetest.get_meta(pos)
+               local inv = meta:get_inventory()
+               inv:set_size('src', 1)
+               inv:set_size('fuel', 1)
+               inv:set_size('dst', 4)
+               furnace_node_timer(pos, 0)
+       end,
+
+       on_metadata_inventory_move = function(pos)
+               minetest.get_node_timer(pos):start(1.0)
+       end,
+       on_metadata_inventory_put = function(pos)
+               -- start timer function, it will sort out whether furnace can burn or not.
+               minetest.get_node_timer(pos):start(1.0)
+       end,
+       on_blast = function(pos)
+               local drops = {}
+               furnace.get_inventory_drops(pos, "src", drops)
+               furnace.get_inventory_drops(pos, "fuel", drops)
+               furnace.get_inventory_drops(pos, "dst", drops)
+               drops[#drops+1] = "default:furnace"
+               minetest.remove_node(pos)
+               return drops
+       end,
+
+       allow_metadata_inventory_put = allow_metadata_inventory_put,
+       allow_metadata_inventory_move = allow_metadata_inventory_move,
+       allow_metadata_inventory_take = allow_metadata_inventory_take,
+})
+
+minetest.register_node("utility:furnace_active", {
+       description = "Furnace",
+       tiles = {
+               "furnace_top.png", "furnace_bottom.png",
+               "furnace_side.png", "furnace_side.png",
+               "furnace_side.png",
+               {
+                       image = "furnace_front_active.png",
+                       backface_culling = false,
+                       animation = {
+                               type = "vertical_frames",
+                               aspect_w = 16,
+                               aspect_h = 16,
+                               length = 1.5
+                       },
+               }
+       },
+       paramtype2 = "facedir",
+       light_source = 8,
+       drop = "default:furnace",
+       groups = {stone=2, not_in_creative_inventory=1},
+       legacy_facedir_simple = true,
+       is_ground_content = false,
+       sounds = main.stoneSound(),
+       on_timer = furnace_node_timer,
+
+       can_dig = can_dig,
+
+       allow_metadata_inventory_put = allow_metadata_inventory_put,
+       allow_metadata_inventory_move = allow_metadata_inventory_move,
+       allow_metadata_inventory_take = allow_metadata_inventory_take,
+})
+
+minetest.register_craft({
+       output = "utility:furnace",
+       recipe = {
+               {"main:stone", "main:stone", "main:stone"},
+               {"main:stone", "",           "main:stone"},
+               {"main:stone", "main:stone", "main:stone"},
+       }
+})
index efc4ec6082dbc1ee5d6e167fca72d2a712af1d27..95af0f8894914e6d14cbeafa8cb9ff2e8dfc4efd 100644 (file)
--- a/todo.txt
+++ b/todo.txt
@@ -7,7 +7,7 @@
 --add treecapitator
 --itemstack max 1000
 --ores
-vignette
+--vignette
 furnace
 crafting recipes
 make trees drop items on treecapitator