diff --git a/ability.lua b/ability.lua index 6189a49..96df13f 100644 --- a/ability.lua +++ b/ability.lua @@ -30,8 +30,8 @@ function magicalities.learn_meets_prerequisites(player_name, item, recipe) if not a[item] then return false end if a[item].depends then local can = true - for v in pairs(a[item].depends) do - if not c(player, v) then + for _,v in pairs(a[item].depends) do + if not c(player_name, v) then can = false break end @@ -50,9 +50,11 @@ function magicalities.available_to_player(player_name, unlocked, researchable) for name,data in pairs(abilities) do local tc = table.copy(data) tc.type = 'ability' - if magicalities.player_has_ability(player_name, name) and unlocked then + if magicalities.player_has_ability(player_name, name) then tc.unlocked = true - table.insert(all, tc) + if unlocked then + table.insert(all, tc) + end elseif magicalities.learn_meets_prerequisites(player_name, name) and researchable then tc.unlocked = false table.insert(all, tc) @@ -63,9 +65,11 @@ function magicalities.available_to_player(player_name, unlocked, researchable) for name,data in pairs(recipes) do local tc = table.copy(data) tc.type = 'recipe' - if magicalities.player_has_recipe(player_name, name) and unlocked then + if magicalities.player_has_recipe(player_name, name) then tc.unlocked = true - table.insert(all, tc) + if unlocked then + table.insert(all, tc) + end elseif magicalities.learn_meets_prerequisites(player_name, name, true) and researchable then tc.unlocked = false table.insert(all, tc) @@ -76,7 +80,7 @@ function magicalities.available_to_player(player_name, unlocked, researchable) end -- Learn a recipe or an ability -function magicalities.player_learn(player_name, item, recipe) +function magicalities.player_learn(player_name, item, recipe, silent) if not magicalities.data[player_name] then magicalities.load_player_data(player_name) end @@ -88,24 +92,28 @@ function magicalities.player_learn(player_name, item, recipe) local recipe_n = recipes[item] if recipe_n then recipe_n = recipe_n.description + table.insert(magicalities.data[player_name].recipes, item) + success = true + msgname = msgname .. recipe_n end - table.insert(magicalities.data[player_name].recipes, item) - success = true - msgname = msgname .. recipe_n elseif not recipe and not magicalities.player_has_ability(player_name, item) then local ability_n = abilities[item] if ability_n then ability_n = ability_n.description + table.insert(magicalities.data[player_name].abilities, item) + success = true + msgname = "to " .. ability_n end - table.insert(magicalities.data[player_name].abilities, item) - success = true - msgname = "to " .. ability_n end if success then magicalities.save_player_data(player_name) - minetest.chat_send_player(player_name, "You have learned " .. msgname .. "!") + if not silent then + minetest.chat_send_player(player_name, "You have learned " .. msgname .. "!") + end end + + return success end -- Add/remove research points diff --git a/book.lua b/book.lua index 22a1201..738ee76 100644 --- a/book.lua +++ b/book.lua @@ -1,7 +1,6 @@ local function book_formspec(user) local avail_list = magicalities.available_to_player(user, true) - print(dump(avail_list)) return "size[5,6]".. default.gui_bg.. default.gui_bg_img.. @@ -22,5 +21,6 @@ minetest.register_craftitem("magicalities:book", { _wand_created = function (itemstack, wand, user, pos) itemstack:get_meta():set_string("player", user:get_player_name()) return itemstack - end + end, + stack_max = 1 }) diff --git a/mod.conf b/mod.conf index b1b6b5f..5d11338 100644 --- a/mod.conf +++ b/mod.conf @@ -1,4 +1,4 @@ name = magicalities description = Magic mod. depends = default -optional_depends = craftguide,fluid_lib,creative +optional_depends = craftguide,fluid_lib,creative,mobs,mobs_animal,dye diff --git a/register.lua b/register.lua index 8ad9a55..86ec5a2 100644 --- a/register.lua +++ b/register.lua @@ -273,6 +273,26 @@ minetest.register_craft({ output = "magicalities:cauldron", }) +if minetest.registered_items["mobs:chicken_feather"] then + minetest.register_craft({ + recipe = { + {"mobs:chicken_feather"}, + {"group:color_black"}, + {"default:glass"} + }, + output = "magicalities:ink_and_quill", + }) +else + minetest.register_craft({ + recipe = { + {"group:color_white"}, + {"group:color_black"}, + {"default:glass"} + }, + output = "magicalities:ink_and_quill", + }) +end + local function _flatten(arr) local result = {} for i,v in ipairs(arr) do @@ -342,7 +362,7 @@ end magicalities.register_ability_learnable({ name = "magicalities:pickup_jarred", - description = "pick up crystals using jars" + description = "Crystal Jarring" }) magicalities.register_recipe_learnable({ diff --git a/research_table.lua b/research_table.lua index 0afee29..678e3c4 100644 --- a/research_table.lua +++ b/research_table.lua @@ -1,17 +1,66 @@ magicalities.researching = {} -local function table_formspec() +local function genlist(list, x, y, w, h, index, canlearn) + local i = "" + if #list == 0 then return "" end + local ty = 0 + local total = #list + local visualtotal = math.ceil(y + h) + local reallist = {} + + for i = index * visualtotal, visualtotal do + if list[i + 1] then + table.insert(reallist, list[i + 1]) + end + end + + for _,v in pairs(reallist) do + if ty + 1 > visualtotal then break end + local icon = "" + + if v.icon ~= nil then + icon = "image["..x..","..(y+ty)..";1,1;"..v.icon.."]" + elseif v.type == "recipe" then + icon = "item_image["..x..","..(y+ty)..";1,1;"..v.name.."]" + end + + i = i .. icon .. "label["..(x + 1)..","..(y+ty)..";"..v.description.."]" + if canlearn then + local t = 1 + if v.type == "recipe" then t = 2 end + i = i .. "button["..(x+w-1)..","..(y+ty)..";1,1;@"..t..""..v.name..";Learn]" + end + ty = ty + 1 + end + + if index > 0 then + i = i .. "button["..(x+w)..","..y..";1,1;up;Up]" + elseif total > visualtotal then + i = i .. "button["..(x+w)..","..(y+h)..";1,1;dn;Down]" + end + + return i +end + +local function table_formspec(player, research, index, canlearn) + local list = {} + + if player then + list = magicalities.available_to_player(player, false, true) + end + return "size[8,8.5]".. default.gui_bg.. default.gui_bg_img.. default.gui_slots.. "image[0.5,0.5;1,1;magicalities_gui_book_slot.png]".. "list[context;book;0.5,0.5;1,1;]".. - "image[1.5,0.5;1,1;magicalities_gui_quill_slot.png]".. - "list[context;tools;1.5,0.5;1,1;]".. - "image[2.5,0.5;1,1;magicalities_gui_paper_slot.png]".. - "list[context;paper;2.5,0.5;3,3;]".. + "image[0.5,1.5;1,1;magicalities_gui_quill_slot.png]".. + "list[context;tools;0.5,1.5;1,1;]".. + "image[0.5,2.5;1,1;magicalities_gui_paper_slot.png]".. + "list[context;paper;0.5,2.5;3,3;]".. + genlist(list, 1.5, 0.5, 5.5, 2, index, canlearn).. "list[current_player;main;0,4.25;8,1;]".. "list[current_player;main;0,5.5;8,3;8]".. "listring[current_player;main]".. @@ -24,11 +73,9 @@ local function table_formspec() default.get_hotbar_bg(0, 4.25) end -local function table_use(pos, node, clicker, itemstack, pointed_thing) - return itemstack -end - local function allow_metadata_inventory_put (pos, listname, index, stack, player) + local meta = minetest.get_meta(pos) + local inv = meta:get_inventory() if minetest.is_protected(pos, player:get_player_name()) then return 0 end @@ -57,6 +104,40 @@ local function allow_metadata_inventory_take (pos, listname, index, stack, playe return stack:get_count() end +local function update_table_formspec(pos) + local meta = minetest.get_meta(pos) + local inv = meta:get_inventory() + local learnable = not inv:get_stack("tools", 1):is_empty() + + if inv:get_stack("book", 1):is_empty() then + meta:set_int("scrolli", 0) + meta:set_string("formspec", table_formspec()) + else + local paper = inv:get_stack("paper", 1) + local bmeta = inv:get_stack("book", 1):get_meta() + local iplayer = bmeta:get_string("player") + local current_research = "" + local current_research_type = 0 + + if not paper:is_empty() then + if paper:get_name() ~= "default:paper" then + learnable = false + end + local pmeta = paper:get_meta() + current_research = pmeta:get_string("learn") + current_research_type = pmeta:get_int("type") + else + learnable = false + end + + if learnable and magicalities.player_research(iplayer) < 10 then + learnable = false + end + + meta:set_string("formspec", table_formspec(iplayer, current_research, meta:get_int("scrolli"), learnable)) + end +end + local function table_inventory_changed (pos, listname, index, stack, player) local meta = minetest.get_meta(pos) local inv = meta:get_inventory() @@ -75,6 +156,100 @@ local function table_inventory_changed (pos, listname, index, stack, player) end minetest.set_node(vec, {name=ver,param2=dir}) end + + update_table_formspec(pos) +end + +local function damage_tools(tools) + local wear = tools:get_wear() + local percent = math.floor(65535 * 0.25) + if wear == 0 then + wear = 65535 - (65535 - percent) + else + wear = wear + percent + end + + if wear <= 65535 and wear >= 0 then + tools:set_wear(wear) + else + return nil + end + + return tools +end + +local function process_learn(pos, ltype, learn, pts, player) + local meta = minetest.get_meta(pos) + local inv = meta:get_inventory() + if inv:get_stack("book", 1):is_empty() or inv:get_stack("tools", 1):is_empty() or inv:get_stack("paper", 1):is_empty() then + return + end + + local bookm = inv:get_stack("book", 1):get_meta() + local player = bookm:get_string("player") + + if player == "" then return end + if inv:get_stack("paper", 1):get_name() ~= "default:paper" then return end + + -- Commit learn + magicalities.deal_research_points(player, -pts) + local istack = ItemStack("magicalities:research_complete") + local istackmeta = istack:get_meta() + istackmeta:set_int("type", ltype) + istackmeta:set_string("learn", learn) + local itool = damage_tools(inv:get_stack("tools", 1)) + inv:set_stack("tools", 1, itool) + if not itool then + table_inventory_changed(pos, "tools", 1, ItemStack(itool), player) + end + inv:set_stack("paper", 1, istack) +end + +local function first_key(list) + local ekey + for key,_ in pairs(list) do + ekey = key + break + end + return ekey +end + +local function table_fields(pos, formname, fields, sender) + local meta = minetest.get_meta(pos) + local findex = meta:get_int("scrolli") + local scrolled = false + local learn_type + local learn + local fkey = first_key(fields) + + if fields["dn"] then + scrolled = true + findex = findex + 1 + elseif fields["up"] then + scrolled = true + findex = findex - 1 + if findex < 0 then + findex = 0 + end + elseif fkey and fkey:sub(0,1) == "@" then + learn_type = tonumber(fkey:sub(2,2)) + learn = fkey:sub(3) + end + + if scrolled then + meta:set_int("scrolli", findex) + end + + if learn and learn_type then + process_learn(pos, learn_type, learn, 10, sender) + end + + update_table_formspec(pos) +end + +local function table_use(pos, node, clicker, itemstack, pointed_thing) + update_table_formspec(pos) + return itemstack end -- Base Table Override @@ -107,6 +282,7 @@ minetest.override_item("magicalities:table", { on_metadata_inventory_take = table_inventory_changed, on_metadata_inventory_put = table_inventory_changed, on_metadata_inventory_move = table_inventory_changed, + on_receive_fields = table_fields, }) -- Remove floating quills diff --git a/table.lua b/table.lua index 65bd7e4..30c555b 100644 --- a/table.lua +++ b/table.lua @@ -80,14 +80,14 @@ function magicalities.arcane.register_recipe(data) recipe_data.name = data.output end data.learnable = recipe_data.name + end + + if not data.description then + local itm = minetest.registered_items[data.output] + recipe_data.description = itm.description else - if not data.description then - local itm = minetest.registered_items[data.output] - recipe_data.description = itm.description - else - recipe_data.description = data.description .. "" - data.description = nil - end + recipe_data.description = data.description .. "" + data.description = nil end magicalities.register_recipe_learnable(recipe_data)