From 04ecb1bd5c321f1c21aeabe9d3c8913c7c9fd8fc Mon Sep 17 00:00:00 2001 From: Duane Date: Fri, 5 Aug 2016 01:29:38 -0500 Subject: [PATCH] Add poison and pit traps. --- abms.lua | 1 - dungeon.lua | 85 ++++++++++++++++++++++++++++++++++++++++++++++++++--- 2 files changed, 81 insertions(+), 5 deletions(-) diff --git a/abms.lua b/abms.lua index bfae8e2..4d45b54 100644 --- a/abms.lua +++ b/abms.lua @@ -359,7 +359,6 @@ minetest.register_abm({ neighbors = {'air'}, interval = 5 * time_factor, chance = 500, - catch_up = false, action = function(pos, node, aoc, active_object_count_wider) if not (pos and node) or active_object_count_wider > dungeon_monster_density then return diff --git a/dungeon.lua b/dungeon.lua index 863baa4..4c79b5c 100644 --- a/dungeon.lua +++ b/dungeon.lua @@ -100,12 +100,70 @@ local chest_formspec = "listring[current_player;main]" .. default.get_hotbar_bg(0,4.85) +local function disintigrate(minp, maxp) + if not (minp and maxp) then + return + end + minp = vector.round(minp) + maxp = vector.round(maxp) + + local air = minetest.get_content_id('air') + local vm = minetest.get_voxel_manip() + if not vm then + return + end + + local emin, emax = vm:read_from_map(minp, maxp) + local area = VoxelArea:new({MinEdge = emin, MaxEdge = emax}) + local data = vm:get_data() + local p = {} + for z = minp.z, maxp.z do + for y = minp.y, maxp.y do + local ivm = area:index(minp.x, y, z) + for x = minp.x, maxp.x do + data[ivm] = air + ivm = ivm + 1 + end + end + end + vm:set_data(data) + vm:write_to_map() + vm:update_map() +end + + +if fun_caves.register_status then + fun_caves.register_status({ + name = 'poisoned', + during = function(player) + if not player then + return + end + + local hp = player:get_hp() + if hp and type(hp) == 'number' then + hp = hp - 1 + player:set_hp(hp) + end + end, + terminate = function(player) + if not player then + return + end + + local player_name = player:get_player_name() + minetest.chat_send_player(player_name, 'Your sickness ebbs away.') + end, + }) +end + + local newnode = fun_caves.clone_node("default:chest") newnode.description = "Treasure Chest" newnode.on_construct = nil newnode.drop = 'default:chest' newnode.on_rightclick = function(pos, node, clicker, itemstack, pointed_thing) - if not pos then + if not (pos and clicker) then return end @@ -118,13 +176,32 @@ newnode.on_rightclick = function(pos, node, clicker, itemstack, pointed_thing) local ready = meta:get_string('formspec') if treasures and ready == '' then - if minetest.get_modpath('tnt') and math.random(20) == 1 then + if math.random(20) == 1 then + local player_name = clicker:get_player_name() + if not player_name or player_name == '' or not fun_caves.set_status then + return + end + minetest.chat_send_player(player_name, minetest.colorize('#FF0000', 'You\'ve been poisoned!')) + fun_caves.set_status(player_name, 'poisoned', 2 ^ math.random(8), {damage = 1}) + return + elseif minetest.get_modpath('tnt') and math.random(20) == 1 then minetest.set_node(pos, {name = 'tnt:tnt_burning'}) local timer = minetest.get_node_timer(pos) if timer then - timer:start(5) + timer:start(3) end minetest.sound_play("default_dig_crumbly", {pos = pos, gain = 0.5, max_hear_distance = 10}) + return + elseif math.random(20) == 1 then + minetest.remove_node(pos) + + pos = clicker:getpos() + if not pos then + return + end + + disintigrate({x = pos.x - 1, y = pos.y - 12, z = pos.z - 1}, {x = pos.x + 1, y = pos.y - 1, z = pos.z + 1}) + return end @@ -390,7 +467,7 @@ fun_caves.dungeon = function(minp_in, maxp_in, data, p2data, area, node, heightm if not leave_alone[data[ivm]] then if ry == 0 and (cy > 0 or not centered_in) then if content[cx][cy][cz] == 'room' then - local r = math.random(5000) + local r = math.random(2000) if r == 1 then data[ivm] = node['fun_caves:stone_with_gold_trap'] elseif r == 2 then