NPC: Cleaned up debugging logs.

Standarized logs to have different levels.
Show by default only INFO, ERROR log messages.
Dialogues: Standarized function for NPC chat messages.
Removed trader.lua and trader_test.lua which are part of old 'mobs_npc' mod.
This commit is contained in:
Hector Franqui 2017-06-17 09:44:25 -04:00
parent bf0f643e3e
commit a91160ecc6
9 changed files with 111 additions and 715 deletions

View File

@ -141,8 +141,8 @@ end
-- and the NPC is allowed to roam freely.
function npc.actions.freeze(self, args)
local freeze_mobs_api = args.freeze
minetest.log("Received: "..dump(freeze_mobs_api))
minetest.log("Returning: "..dump(not(freeze_mobs_api)))
--minetest.log("Received: "..dump(freeze_mobs_api))
--minetest.log("Returning: "..dump(not(freeze_mobs_api)))
return not(freeze_mobs_api)
end
@ -333,7 +333,7 @@ function npc.actions.take_item_from_external_inventory(self, args)
else
inv = minetest.get_inventory({type="node", pos=pos})
end
-- Create ItemSTack to take from external inventory
-- Create ItemStack to take from external inventory
local item = ItemStack(item_name.." "..count)
-- Check if there is enough of the item to take
if inv:contains_item(inv_list, item) then
@ -369,7 +369,7 @@ end
-- TODO: Refactor this function so that it uses a table to check
-- for doors instead of having separate logic for each door type
function npc.actions.get_openable_node_state(node, npc_dir)
minetest.log("Node name: "..dump(node.name))
--minetest.log("Node name: "..dump(node.name))
local state = npc.actions.const.doors.state.CLOSED
-- Check for default doors and gates
local a_i1, a_i2 = string.find(node.name, "_a")
@ -383,7 +383,7 @@ function npc.actions.get_openable_node_state(node, npc_dir)
if a_i1 == nil and open_i1 == nil and not half_door_is_closed then
state = npc.actions.const.doors.state.OPEN
end
minetest.log("Door state: "..dump(state))
--minetest.log("Door state: "..dump(state))
return state
end
@ -412,10 +412,10 @@ end
-- items from a chest, are provided here.
local function get_pos_argument(self, pos)
minetest.log("Type of pos: "..dump(type(pos)))
--minetest.log("Type of pos: "..dump(type(pos)))
-- Check which type of position argument we received
if type(pos) == "table" then
minetest.log("Received table pos: "..dump(pos))
--minetest.log("Received table pos: "..dump(pos))
-- Check if table is position
if pos.x ~= nil and pos.y ~= nil and pos.z ~= nil then
-- Position received, return position
@ -468,7 +468,7 @@ end
function npc.actions.use_furnace(self, args)
local pos = get_pos_argument(self, args.pos)
if pos == nil then
minetest.log("[advanced_npc] WARNING Got nil position in 'use_furnace' using args.pos: "..dump(args.pos))
npc.log("WARNING", "Got nil position in 'use_furnace' using args.pos: "..dump(args.pos))
return
end
@ -478,14 +478,14 @@ function npc.actions.use_furnace(self, args)
-- will mainly use this as fuels to avoid getting useful
-- items (such as coal lumps) for burning
local fuels = {"default:leaves",
"default:pine_needles",
"default:tree",
"default:acacia_tree",
"default:aspen_tree",
"default:jungletree",
"default:pine_tree",
"default:coalblock",
"farming:straw"}
"default:pine_needles",
"default:tree",
"default:acacia_tree",
"default:aspen_tree",
"default:jungletree",
"default:pine_tree",
"default:coalblock",
"farming:straw"}
-- Check if NPC has item to cook
local src_item = npc.inventory_contains(self, npc.get_item_name(item))
@ -503,15 +503,15 @@ function npc.actions.use_furnace(self, args)
local fuel_time =
minetest.get_craft_result({method="fuel", width=1, items={ItemStack(fuel_item.item_string)}}).time
local total_fuel_time = fuel_time * npc.get_item_count(fuel_item.item_string)
minetest.log("Fuel time: "..dump(fuel_time))
npc.log("DEBUG", "Fuel time: "..dump(fuel_time))
-- Get item to cook's cooking time
local cook_result =
minetest.get_craft_result({method="cooking", width=1, items={ItemStack(src_item.item_string)}})
local total_cook_time = cook_result.time * npc.get_item_count(item)
minetest.log("Cook: "..dump(cook_result))
npc.log("DEBUG", "Cook: "..dump(cook_result))
minetest.log("Total cook time: "..total_cook_time
npc.log("DEBUG", "Total cook time: "..total_cook_time
..", total fuel burn time: "..dump(total_fuel_time))
-- Check if there is enough fuel to cook all items
@ -531,7 +531,7 @@ function npc.actions.use_furnace(self, args)
fuel_amount = 1
end
minetest.log("Amount of fuel needed: "..fuel_amount)
npc.log("DEBUG", "Amount of fuel needed: "..fuel_amount)
-- Put this item on the fuel inventory list of the furnace
local args = {
@ -554,7 +554,7 @@ function npc.actions.use_furnace(self, args)
npc.add_action(self, npc.actions.cmd.PUT_ITEM, args)
-- Now, set NPC to wait until furnace is done.
minetest.log("Setting wait action for "..dump(total_cook_time))
npc.log("DEBUG", "Setting wait action for "..dump(total_cook_time))
npc.add_action(self, npc.actions.cmd.SET_INTERVAL, {interval=total_cook_time, freeze=freeze})
-- Reset timer
@ -563,7 +563,7 @@ function npc.actions.use_furnace(self, args)
-- If freeze is false, then we will have to find the way back to the furnace
-- once cooking is done.
if freeze == false then
minetest.log("Adding walk to position to wandering: "..dump(pos))
npc.log("DEBUG", "Adding walk to position to wandering: "..dump(pos))
npc.add_task(self, npc.actions.cmd.WALK_TO_POS, {end_pos=pos, walkable={}})
end
@ -577,10 +577,10 @@ function npc.actions.use_furnace(self, args)
count = npc.get_item_count(item),
is_furnace = false
}
minetest.log("Taking item back: "..minetest.pos_to_string(pos))
npc.log("DEBUG", "Taking item back: "..minetest.pos_to_string(pos))
npc.add_action(self, npc.actions.cmd.TAKE_ITEM, args)
minetest.log("Inventory: "..dump(self.inventory))
npc.log("DEBUG", "Inventory: "..dump(self.inventory))
return true
end
@ -594,7 +594,7 @@ end
function npc.actions.use_bed(self, args)
local pos = get_pos_argument(self, args.pos)
if pos == nil then
minetest.log("[advanced_npc] WARNING Got nil position in 'use_bed' using args.pos: "..dump(args.pos))
npc.log("WARNING", "Got nil position in 'use_bed' using args.pos: "..dump(args.pos))
return
end
local action = args.action
@ -654,7 +654,7 @@ end
function npc.actions.use_sittable(self, args)
local pos = get_pos_argument(self, args.pos)
if pos == nil then
minetest.log("[advanced_npc] WARNING Got nil position in 'use_sittable' using args.pos: "..dump(args.pos))
npc.log("WARNING", "Got nil position in 'use_sittable' using args.pos: "..dump(args.pos))
return
end
local action = args.action
@ -727,7 +727,7 @@ function npc.actions.walk_to_pos(self, args)
-- Get arguments for this task
local end_pos = get_pos_argument(self, args.end_pos)
if end_pos == nil then
minetest.log("[advanced_npc] WARNING Got nil position in 'walk_to_pos' using args.pos: "..dump(args.end_pos))
npc.log("WARNING", "Got nil position in 'walk_to_pos' using args.pos: "..dump(args.end_pos))
return
end
local enforce_move = args.enforce_move or true
@ -737,8 +737,8 @@ function npc.actions.walk_to_pos(self, args)
local start_pos = vector.round(self.object:getpos())
-- Use y of end_pos (this can only be done assuming flat terrain)
--start_pos.y = self.object:getpos().y
minetest.log("[advanced_npc] INFO walk_to_pos: Start pos: "..minetest.pos_to_string(start_pos))
minetest.log("[advanced_npc] INFO walk_to_pos: End pos: "..minetest.pos_to_string(end_pos))
npc.log("DEBUG", "walk_to_pos: Start pos: "..minetest.pos_to_string(start_pos))
npc.log("DEBUG", "walk_to_pos: End pos: "..minetest.pos_to_string(end_pos))
-- Set walkable nodes to empty if the parameter hasn't been used
if walkable_nodes == nil then
@ -759,11 +759,8 @@ function npc.actions.walk_to_pos(self, args)
end
path = path_detail
--minetest.log("Found path: "..dump(path))
--minetest.log("Path detail: "..dump(path_detail))
--minetest.log("New path: "..dump(path))
minetest.log("[advanced_npc] INFO walk_to_pos Found path to node: "..minetest.pos_to_string(end_pos))
npc.log("DEBUG", "Detailed path: "..dump(path))
npc.log("INFO", "walk_to_pos Found path to node: "..minetest.pos_to_string(end_pos))
-- Store path
self.actions.walking.path = path
@ -784,6 +781,8 @@ function npc.actions.walk_to_pos(self, args)
if (i+1) == #path then
-- Add direction to last node
local dir = npc.actions.get_direction(path[i].pos, end_pos)
-- Add the last step
npc.add_action(self, npc.actions.cmd.WALK_STEP, {dir = dir, speed = speed, target_pos = path[i+1].pos})
-- Add stand animation at end
npc.add_action(self, npc.actions.cmd.STAND, {dir = dir})
break
@ -823,7 +822,7 @@ function npc.actions.walk_to_pos(self, args)
-- end
-- local pos_on_close = {x=path[i+1].pos.x + x_adj, y=path[i+1].pos.y + 1, z=path[i+1].pos.z + z_adj}
-- Add extra walk step to ensure that one is standing at other side of openable node
npc.add_action(self, npc.actions.cmd.WALK_STEP, {dir = dir, speed = speed, target_pos = path[i+2].pos})
-- npc.add_action(self, npc.actions.cmd.WALK_STEP, {dir = dir, speed = speed, target_pos = path[i+2].pos})
-- Stop to close the door
npc.add_action(self, npc.actions.cmd.STAND, {dir=(dir + 2) % 4 })--, pos=pos_on_close})
-- Close door
@ -840,7 +839,7 @@ function npc.actions.walk_to_pos(self, args)
else
-- Unable to find path
minetest.log("[advanced_npc] INFO walk_to_pos Unable to find path. Teleporting to: "..minetest.pos_to_string(end_pos))
npc.log("WARNING", "walk_to_pos Unable to find path. Teleporting to: "..minetest.pos_to_string(end_pos))
-- Check if movement is enforced
if enforce_move then
-- Move to end pos

View File

@ -124,7 +124,7 @@ function npc.places.find_node_orthogonally(pos, nodes, y_adjustment)
local result = {}
for _,point in pairs(points) do
local node = minetest.get_node(point)
minetest.log("Found node: "..dump(node)..", at pos: "..dump(point))
--minetest.log("Found node: "..dump(node)..", at pos: "..dump(point))
for _,node_name in pairs(nodes) do
if node.name == node_name then
table.insert(result, {name=node.name, pos=point, param2=node.param2})
@ -194,8 +194,8 @@ function npc.places.find_entrance_from_openable_nodes(all_openable_nodes, marker
--local path = pathfinder.find_path(start_pos, end_pos, 20, {})
local entity = {}
entity.collisionbox = {-0.20,-1.0,-0.20, 0.20,0.8,0.20}
minetest.log("Start pos: "..minetest.pos_to_string(start_pos))
minetest.log("End pos: "..minetest.pos_to_string(end_pos))
--minetest.log("Start pos: "..minetest.pos_to_string(start_pos))
--minetest.log("End pos: "..minetest.pos_to_string(end_pos))
local path = pathfinder.find_path(start_pos, end_pos, entity)
--minetest.log("Found path: "..dump(path))
if path ~= nil then
@ -217,13 +217,13 @@ function npc.places.find_entrance_from_openable_nodes(all_openable_nodes, marker
-- Check if min-distance door is a cottages door
-- while we have a MTG door
if min_node_name == "cottages:half_door" and doors_st ~= nil then
minetest.log("Assigned new door...")
--minetest.log("Assigned new door...")
min = #path
result = openable_nodes[i]
end
end
else
minetest.log("Path not found to marker from "..minetest.pos_to_string(start_pos))
npc.log("ERROR", "Path not found to marker from "..minetest.pos_to_string(start_pos))
end
end
end
@ -302,7 +302,7 @@ function npc.places.is_in_staircase(pos)
-- Get next node
local upper_node = minetest.get_node(upper_pos)
local lower_node = minetest.get_node(lower_pos)
minetest.log("Next node: "..dump(upper_pos))
--minetest.log("Next node: "..dump(upper_pos))
-- Check if next node is also a stairs node
local up_p1, up_p2 = string.find(upper_node.name, "stairs:")
local lo_p1, lo_p2 = string.find(lower_node.name, "stairs:")
@ -351,7 +351,7 @@ end
-- front of a door. Used to make NPCs exit buildings.
function npc.places.find_node_in_front_of_door(door_pos)
local door = minetest.get_node(door_pos)
minetest.log("Param2 of door: "..dump(door.param2))
--minetest.log("Param2 of door: "..dump(door.param2))
if door.param2 == 0 then
-- Looking south
return {x=door_pos.x, y=door_pos.y, z=door_pos.z - 1}

View File

@ -296,7 +296,7 @@ function npc.dialogue.process_dialogue(self, dialogue, player_name)
-- Send dialogue line
if dialogue.text then
minetest.chat_send_player(player_name, self.npc_name..": "..dialogue.text)
npc.chat(self.npc_name, player_name, dialogue.text)
end
-- Check if dialogue has responses. If it doesn't, unlock the actions

View File

@ -23,7 +23,6 @@ else
end
mobs.intllib = S
-- NPC
dofile(path .. "/npc.lua")
dofile(path .. "/spawner.lua")
dofile(path .. "/relationships.lua")

46
npc.lua
View File

@ -42,9 +42,27 @@ npc.action_state = {
interrupted = 2
}
npc.log_level = {
INFO = true,
WARNING = false,
ERROR = true,
DEBUG = false
}
---------------------------------------------------------------------------------------
-- General functions
---------------------------------------------------------------------------------------
-- Logging
function npc.log(level, message)
if npc.log_level[level] then
minetest.log("[advanced_npc] "..type..": "..message)
end
end
-- NPC chat
function npc.chat(npc_name, player_name, message)
minetest.chat_send_player(player_name, npc_name..": "..message)
-- Gets name of player or NPC
function npc.get_entity_name(entity)
if entity:is_player() then
@ -176,7 +194,7 @@ end
-- Spawn function. Initializes all variables that the
-- NPC will have and choose random, starting values
function npc.initialize(entity, pos, is_lua_entity, npc_stats)
minetest.log("[advanced_npc] INFO: Initializing NPC at "..minetest.pos_to_string(pos))
npc.log("INFO", "Initializing NPC at "..minetest.pos_to_string(pos))
-- Get variables
local ent = entity
@ -426,7 +444,7 @@ function npc.initialize(entity, pos, is_lua_entity, npc_stats)
table.insert(ent.trader_data.custom_trades, offer2)
--minetest.log(dump(ent))
minetest.log("[advanced_npc] INFO Successfully initialized NPC with name "..dump(ent.npc_name))
npc.log("INFO", "Successfully initialized NPC with name "..dump(ent.npc_name))
-- Refreshes entity
ent.object:set_properties(ent)
end
@ -596,7 +614,7 @@ end
function npc.execute_action(self)
-- Check if an action was interrupted
if self.actions.current_action_state == npc.action_state.interrupted then
minetest.log("[advanced_npc] DEBUG Re-inserting interrupted action for NPC: '"..dump(self.npc_name).."': "..dump(self.actions.state_before_lock.interrupted_action))
npc.log("DEBUG", "Re-inserting interrupted action for NPC: '"..dump(self.npc_name).."': "..dump(self.actions.state_before_lock.interrupted_action))
-- Insert into queue the interrupted action
table.insert(self.actions.queue, 1, self.actions.state_before_lock.interrupted_action)
-- Clear the action
@ -618,7 +636,7 @@ function npc.execute_action(self)
-- If the entry is a task, then push all this new operations in
-- stack fashion
if action_obj.is_task == true then
minetest.log("[advanced_npc] DEBUG Executing task for NPC '"..dump(self.npc_name).."': "..dump(action_obj))
npc.log("DEBUG", "Executing task for NPC '"..dump(self.npc_name).."': "..dump(action_obj))
-- Backup current queue
local backup_queue = self.actions.queue
-- Remove this "task" action from queue
@ -634,7 +652,7 @@ function npc.execute_action(self)
table.insert(self.actions.queue, backup_queue[i])
end
else
minetest.log("[advanced_npc] DEBUG Executing action for NPC '"..dump(self.npc_name).."': "..dump(action_obj))
npc.log("DEBUG", "Executing action for NPC '"..dump(self.npc_name).."': "..dump(action_obj))
-- Store the action that is being executed
self.actions.state_before_lock.interrupted_action = action_obj
-- Store current position
@ -689,7 +707,7 @@ function npc.lock_actions(self)
-- Freeze mobs_redo API
self.freeze = false
minetest.log("Locking")
npc.log("DEBUG", "Locking NPC "..dump(self.npc_id).." actions")
end
function npc.unlock_actions(self)
@ -703,7 +721,7 @@ function npc.unlock_actions(self)
self.freeze = true
end
minetest.log("Unlocked")
npc.log("DEBUG", "Unlocked NPC "..dump(self.npc_id).." actions")
end
---------------------------------------------------------------------------------------
@ -863,7 +881,7 @@ mobs:register_mob("advanced_npc:npc", {
{"npc_female1.png"}, -- female by nuttmeg20
},
child_texture = {
{"npc_baby_male1.png"}, -- derpy baby by AmirDerAssassine
{"npc_baby_male1.png"},
{"npc_baby_female1.png"},
},
makes_footstep_sound = true,
@ -915,12 +933,8 @@ mobs:register_mob("advanced_npc:npc", {
--self.base_texture = "mobs_npc_child_male1.png"
--self.object:set_properties(self)
minetest.log(dump(self))
npc.log("DEBUG", "Right-clicked NPC: "..dump(self))
minetest.log("Child: "..dump(self.is_child))
minetest.log("Sex: "..dump(self.sex))
minetest.log("Textures: "..dump(self.textures))
-- Receive gift or start chat. If player has no item in hand
-- then it is going to start chat directly
if self.can_have_relationship and item:to_table() ~= nil then
@ -952,7 +966,7 @@ mobs:register_mob("advanced_npc:npc", {
-- Initialize NPC if spawned using the spawn egg built in from
-- mobs_redo. This functionality will be removed in the future in
-- favor of a better manual spawning method with customization
minetest.log("[advanced_npc] WARNING: Initializing NPC from entity step. This message should only be appearing if an NPC is being spawned from inventory with egg!")
npc.log("WARNING", "Initializing NPC from entity step. This message should only be appearing if an NPC is being spawned from inventory with egg!")
npc.initialize(self, self.object:getpos(), true)
else
self.tamed = false
@ -1049,7 +1063,7 @@ mobs:register_mob("advanced_npc:npc", {
-- to action queue. This is for jobs.
-- TODO: Need to implement
else
minetest.log("Adding actions to action queue")
npc.log("DEBUG", "Adding actions to action queue")
-- Add to action queue all actions on schedule
for i = 1, #schedule[time] do
if schedule[time][i].action == nil then
@ -1060,7 +1074,7 @@ mobs:register_mob("advanced_npc:npc", {
npc.add_action(self, schedule[time][i].action, schedule[time][i].args)
end
end
minetest.log("New action queue: "..dump(self.actions))
npc.log("DEBUG", "New action queue: "..dump(self.actions))
end
end
end

View File

@ -209,7 +209,7 @@ function spawner.assign_places(self, pos)
-- Find unowned bed
for i = 1, #node_data.bed_type do
-- Check if bed has owner
minetest.log("Node: "..dump(node_data.bed_type[i]))
--minetest.log("Node: "..dump(node_data.bed_type[i]))
if node_data.bed_type[i].owner == "" then
-- If bed has no owner, check if it is accessible
local empty_nodes = npc.places.find_node_orthogonally(
@ -223,7 +223,7 @@ function spawner.assign_places(self, pos)
npc.places.PLACE_TYPE.BED.PRIMARY, node_data.bed_type[i].node_pos, empty_nodes[1].pos)
-- Store changes to node_data
meta:set_string("node_data", minetest.serialize(node_data))
minetest.log("Added bed at "..minetest.pos_to_string(node_data.bed_type[i].node_pos)
npc.log("DEBUG", "Added bed at "..minetest.pos_to_string(node_data.bed_type[i].node_pos)
.." to NPC "..dump(self.npc_name))
break
end
@ -233,7 +233,7 @@ function spawner.assign_places(self, pos)
--local plot_info = minetest.deserialize(meta:get_string("plot_info"))
--minetest.log("Plot info:"..dump(plot_info))
minetest.log("places: "..dump(self.places_map))
npc.log("DEBUG", "Places for NPC "..self.npc_name..": "..dump(self.places_map))
-- Make NPC go into their house
npc.add_task(self,
@ -274,9 +274,9 @@ function npc.spawner.spawn_npc(pos)
-- Check amount of NPCs that should be spawned
local npc_count = meta:get_int("npc_count")
local spawned_npc_count = meta:get_int("spawned_npc_count")
minetest.log("[advanced_npc] INFO Currently spawned "..dump(spawned_npc_count).." of "..dump(npc_count).." NPCs")
npc.log("INFO", "Currently spawned "..dump(spawned_npc_count).." of "..dump(npc_count).." NPCs")
if spawned_npc_count < npc_count then
minetest.log("[advanced_npc] INFO Spawning NPC at "..minetest.pos_to_string(pos))
npc.log("INFO", "Spawning NPC at "..minetest.pos_to_string(pos))
-- Spawn a NPC
local ent = minetest.add_entity({x=pos.x, y=pos.y+1, z=pos.z}, "advanced_npc:npc")
if ent and ent:get_luaentity() then
@ -324,21 +324,21 @@ function npc.spawner.spawn_npc(pos)
meta:set_string("npc_stats", minetest.serialize(npc_stats))
-- Temp
--meta:set_string("infotext", meta:get_string("infotext")..", "..spawned_npc_count)
minetest.log("[advanced_npc] INFO Spawning successful!")
npc.log("INFO", "Spawning successful!")
-- Check if there are more NPCs to spawn
if spawned_npc_count >= npc_count then
-- Stop timer
minetest.log("[advanced_npc] INFO No more NPCs to spawn at this location")
npc.log("INFO", "No more NPCs to spawn at this location")
timer:stop()
else
-- Start another timer to spawn more NPC
local new_delay = math.random(npc.spawner.spawn_delay)
minetest.log("[advanced_npc] INFO Spawning one more NPC in "..dump(npc.spawner.spawn_delay).."s")
npc.log("INFO", "Spawning one more NPC in "..dump(npc.spawner.spawn_delay).."s")
timer:start(new_delay)
end
return true
else
minetest.log("[advanced_npc] Spawning failed!")
npc.log("ERROR", "Spawning failed!")
ent:remove()
return false
end
@ -358,13 +358,13 @@ function spawner.calculate_npc_spawning(pos)
-- Get nodes for this building
local node_data = minetest.deserialize(meta:get_string("node_data"))
if node_data == nil then
minetest.log("[advanced_npc] ERROR: Mis-configured advanced_npc:plotmarker_auto_spawner at position: "..minetest.pos_to_string(pos))
npc.log("ERROR", "Mis-configured advanced_npc:plotmarker_auto_spawner at position: "..minetest.pos_to_string(pos))
return
end
-- Check number of beds
local beds_count = #node_data.bed_type--#spawner.filter_first_floor_nodes(node_data.bed_type, pos)
minetest.log("[advanced_npc] INFO: Found "..dump(beds_count).." beds in the building at "..minetest.pos_to_string(pos))
npc.log("DEBUG", "Found "..dump(beds_count).." beds in the building at "..minetest.pos_to_string(pos))
local npc_count = 0
-- If number of beds is zero or beds/2 is less than one, spawn
-- a single NPC.
@ -375,7 +375,7 @@ function spawner.calculate_npc_spawning(pos)
-- Spawn (beds_count/2) NPCs
npc_count = ((beds_count / 2) - ((beds_count / 2) % 1))
end
minetest.log("[advanced_npc] INFO: Will spawn "..dump(npc_count).." NPCs at "..minetest.pos_to_string(pos))
npc.log("INFO", "Will spawn "..dump(npc_count).." NPCs at "..minetest.pos_to_string(pos))
-- Store amount of NPCs to spawn
meta:set_int("npc_count", npc_count)
-- Store amount of NPCs spawned
@ -435,14 +435,14 @@ function spawner.scan_mg_villages_building(pos, building_data)
--minetest.set_node({x=pos.x,y=pos.y,z=pos.z + (z_sign * z_size)}, {name = "wool:blue"})
--minetest.get_meta({x=pos.x,y=pos.y,z=pos.z + (z_sign * z_size)}):set_string("infotext", minetest.get_meta(pos):get_string("infotext")..", Axis: z, Sign: "..dump(z_sign))
minetest.log("Start pos: "..minetest.pos_to_string(start_pos))
minetest.log("Plot: "..dump(minetest.get_meta(start_pos):get_string("infotext")))
npc.log("DEBUG", "Start pos: "..minetest.pos_to_string(start_pos))
npc.log("DEBUG", "Plot: "..dump(minetest.get_meta(start_pos):get_string("infotext")))
minetest.log("Brotate: "..dump(brotate))
minetest.log("X_sign: "..dump(x_sign))
minetest.log("X_adj: "..dump(x_sign*x_size))
minetest.log("Z_sign: "..dump(z_sign))
minetest.log("Z_adj: "..dump(z_sign*z_size))
npc.log("DEBUG", "Brotate: "..dump(brotate))
npc.log("DEBUG", "X_sign: "..dump(x_sign))
npc.log("DEBUG", "X_adj: "..dump(x_sign*x_size))
npc.log("DEBUG", "Z_sign: "..dump(z_sign))
npc.log("DEBUG", "Z_adj: "..dump(z_sign*z_size))
local end_pos = {x=pos.x + (x_sign * x_size), y=pos.y + y_size, z=pos.z + (z_sign * z_size)}
@ -451,7 +451,7 @@ function spawner.scan_mg_villages_building(pos, building_data)
--minetest.set_node(end_pos, {name="default:mese_block"})
--minetest.get_meta(end_pos):set_string("infotext", minetest.get_meta(start_pos):get_string("infotext"))
minetest.log("Calculated end pos: "..minetest.pos_to_string(end_pos))
npc.log("DEBUG", "Calculated end pos: "..minetest.pos_to_string(end_pos))
return spawner.scan_area(start_pos, end_pos)
end
@ -477,7 +477,7 @@ function spawner.replace_mg_villages_plotmarker(pos)
if building_type == value then
minetest.log("Replacing mg_villages:plotmarker at "..minetest.pos_to_string(pos))
npc.log("INFO", "Replacing mg_villages:plotmarker at "..minetest.pos_to_string(pos))
-- Replace the plotmarker for auto-spawner
minetest.set_node(pos, {name="advanced_npc:plotmarker_auto_spawner"})
-- Store old plotmarker metadata again
@ -498,9 +498,9 @@ function spawner.replace_mg_villages_plotmarker(pos)
--minetest.log("Found "..dump(#doors).." openable nodes")
local entrance = npc.places.find_entrance_from_openable_nodes(doors, pos)
if entrance then
minetest.log("Found building entrance at: "..minetest.pos_to_string(entrance.node_pos))
npc.log("INFO", "Found building entrance at: "..minetest.pos_to_string(entrance.node_pos))
else
minetest.log("Unable to find building entrance!")
npc.log("ERROR", "Unable to find building entrance!")
end
-- Store building entrance
meta:set_string("entrance", minetest.serialize(entrance))
@ -569,7 +569,7 @@ if minetest.get_modpath("mg_villages") ~= nil then
-- end
-- minetest.get_meta(pos):set_string("node_data", minetest.serialize(nodedata))
-- minetest.log("Cleared bed owners")
minetest.log("NPC stats: "..dump(minetest.deserialize(minetest.get_meta(pos):get_string("npc_stats"))))
--minetest.log("NPC stats: "..dump(minetest.deserialize(minetest.get_meta(pos):get_string("npc_stats"))))
return mg_villages.plotmarker_formspec( pos, nil, {}, clicker )
end,
@ -610,7 +610,7 @@ if minetest.get_modpath("mg_villages") ~= nil then
-- end
-- })
-- ABM Registration... for when LBM fails.
-- ABM Registration
minetest.register_abm({
label = "Replace mg_villages:plotmarker with Advanced NPC auto spawners",
nodenames = {"mg_villages:plotmarker"},

View File

@ -415,8 +415,8 @@ function npc.trade.get_dedicated_trade_offers(self)
-- If item found, create a buy offer for this item
-- Again, offers are created for one item only. Buy offers should be removed
-- after the NPC has bought a certain quantity, say, 5 items.
minetest.log("Item: "..item_name)
minetest.log("Trade info: "..dump(trade_info))
--minetest.log("Item: "..item_name)
--minetest.log("Trade info: "..dump(trade_info))
--minetest.log("Logic: "..dump(trade_info.item_bought_count == nil
-- or (trade_info.item_bought_count ~= nil and trade_info.item_bought_count <= npc.trade.DEDICATED_MAX_BUY_AMOUNT)))
if trade_info.item_bought_count == nil
@ -537,16 +537,17 @@ function npc.trade.perform_trade(self, player_name, offer)
inv:add_item("main", price_stacks[j])
end
-- Send message to player
minetest.chat_send_player(player_name, "Thank you!")
npc.chat(self.npc_name, player_name, "Thank you!")
return true
else
minetest.chat_send_player(player_name,
npc.chat(self.npc_name, player_name,
"Looks like you can't get what I'm giving you for payment!")
return false
end
end
else
minetest.chat_send_player(player_name, "Looks like you don't have what I want to buy...")
npc.chat(self.npc_name, player_name,
"Looks like you don't have what I want to buy...")
return false
end
else
@ -570,14 +571,16 @@ function npc.trade.perform_trade(self, player_name, offer)
-- Add item items to player
inv:add_item("main", item_stack)
-- Send message to player
minetest.chat_send_player(player_name, "Thank you!")
npc.chat(self.npc_name, player_name, "Thank you!")
return true
else
minetest.chat_send_player(player_name, "Looks like you can't carry anything else...")
npc.chat(self.npc_name, player_name,
"Looks like you can't carry anything else...")
return false
end
else
minetest.chat_send_player(player_name, "Looks like you don't have what I'm asking for!")
npc.chat(self.npc_name, player_name,
"Looks like you don't have what I'm asking for!")
return false
end
end
@ -624,8 +627,8 @@ minetest.register_on_player_receive_fields(function (player, formname, fields)
if player_response.offers_type == npc.trade.OFFER_BUY then
-- Increase the item bought count
local offer_item_name = npc.get_item_name(trade_offers[i].item)
minetest.log("Bought item name: "..dump(offer_item_name))
minetest.log(dump(player_response.npc.trader_data.trade_list.both[offer_item_name]))
--minetest.log("Bought item name: "..dump(offer_item_name))
--minetest.log(dump(player_response.npc.trader_data.trade_list.both[offer_item_name]))
-- Check if this item has been bought before
if player_response.npc.trader_data.trade_list.both[offer_item_name].item_bought_count == nil then
-- Set first count to 1

View File

@ -1,355 +0,0 @@
local S = mobs.intllib
mobs.human = {
items = {
--{item for sale, price, chance of appearing in trader's inventory}
{"default:apple 10", "default:gold_ingot 2", 10},
{"farming:bread 10", "default:gold_ingot 4", 5},
{"default:clay 10", "default:gold_ingot 2", 12},
{"default:brick 10", "default:gold_ingot 4", 17},
{"default:glass 10", "default:gold_ingot 4", 17},
{"default:obsidian 10", "default:gold_ingot 15", 50},
{"default:diamond 1", "default:gold_ingot 5", 40},
{"farming:wheat 10", "default:gold_ingot 2", 17},
{"default:tree 5", "default:gold_ingot 4", 20},
{"default:stone 10", "default:gold_ingot 8", 17},
{"default:desert_stone 10", "default:gold_ingot 8", 27},
{"default:sapling 1", "default:gold_ingot 1", 7},
{"default:pick_steel 1", "default:gold_ingot 2", 7},
{"default:sword_steel 1", "default:gold_ingot 2", 17},
{"default:shovel_steel 1", "default:gold_ingot 1", 17},
},
names = {
"Bob", "Duncan", "Bill", "Tom", "James", "Ian", "Lenny"
}
}
-- Trader ( same as NPC but with right-click shop )
mobs:register_mob("mobs_npc:trader", {
type = "npc",
passive = false,
damage = 3,
attack_type = "dogfight",
attacks_monsters = true,
pathfinding = false,
hp_min = 10,
hp_max = 20,
armor = 100,
collisionbox = {-0.35,-1.0,-0.35, 0.35,0.8,0.35},
visual = "mesh",
mesh = "character.b3d",
textures = {
{"mobs_trader.png"}, -- by Frerin
},
makes_footstep_sound = true,
sounds = {},
walk_velocity = 2,
run_velocity = 3,
jump = false,
drops = {},
water_damage = 0,
lava_damage = 4,
light_damage = 0,
follow = {"default:diamond"},
view_range = 15,
owner = "",
order = "stand",
fear_height = 3,
animation = {
speed_normal = 30,
speed_run = 30,
stand_start = 0,
stand_end = 79,
walk_start = 168,
walk_end = 187,
run_start = 168,
run_end = 187,
punch_start = 200,
punch_end = 219,
},
on_rightclick = function(self, clicker)
mobs_trader(self, clicker, entity, mobs.human)
end,
})
--This code comes almost exclusively from the trader and inventory of mobf, by Sapier.
--The copyright notice below is from mobf:
-------------------------------------------------------------------------------
-- Mob Framework Mod by Sapier
--
-- You may copy, use, modify or do nearly anything except removing this
-- copyright notice.
-- And of course you are NOT allow to pretend you have written it.
--
--! @file inventory.lua
--! @brief component containing mob inventory related functions
--! @copyright Sapier
--! @author Sapier
--! @date 2013-01-02
--
--! @defgroup Inventory Inventory subcomponent
--! @brief Component handling mob inventory
--! @ingroup framework_int
--! @{
--
-- Contact sapier a t gmx net
-------------------------------------------------------------------------------
function mobs.allow_move(inv, from_list, from_index, to_list, to_index, count, player)
if to_list ~= "selection"
or from_list == "price"
or from_list == "payment"
or from_list == "takeaway"
or from_list == "identifier" then
return 0
end
-- forbid moving split stacks
local old_stack = inv.get_stack(inv, from_list, from_index)
if count ~= old_stack.get_count(old_stack) then
return 0
end
return count
end
function mobs.allow_put(inv, listname, index, stack, player)
if listname == "payment" then
return 99
end
return 0
end
function mobs.allow_take(inv, listname, index, stack, player)
if listname == "takeaway"
or listname == "payment" then
return 99
else
return 0
end
end
function mobs.on_put(inv, listname, index, stack)
if listname == "payment" then
mobs.update_takeaway(inv)
end
end
function mobs.on_take(inv, listname, count, index, stack, player)
if listname == "takeaway" then
local amount = inv:get_stack("payment", 1):get_count()
local price = inv:get_stack("price", 1):get_count()
local thing = inv:get_stack("payment", 1):get_name()
inv.set_stack(inv,"selection", 1, nil)
inv.set_stack(inv,"price", 1, nil)
inv.set_stack(inv,"takeaway", 1, nil)
inv.set_stack(inv,"payment", 1, thing .. " " .. amount - price)
end
if listname == "payment" then
if mobs.check_pay(inv, false) then
local selection = inv.get_stack(inv, "selection", 1)
if selection ~= nil then
inv.set_stack(inv,"takeaway", 1, selection)
end
else
inv.set_stack(inv, "takeaway", 1, nil)
end
end
end
function mobs.update_takeaway(inv)
if mobs.check_pay(inv,false) then
local selection = inv.get_stack(inv,"selection", 1)
if selection ~= nil then
inv.set_stack(inv,"takeaway", 1, selection)
end
else
inv.set_stack(inv,"takeaway", 1, nil)
end
end
function mobs.check_pay(inv, paynow)
local now_at_pay = inv.get_stack(inv,"payment", 1)
local count = now_at_pay.get_count(now_at_pay)
local name = now_at_pay.get_name(now_at_pay)
local price = inv.get_stack(inv, "price", 1)
if price:get_name() == name then
local price = price:get_count()
if price > 0
and price <= count then
if paynow then
now_at_pay.take_item(now_at_pay, price)
inv.set_stack(inv,"payment", 1, now_at_pay)
return true
else
return true
end
else
if paynow then
inv.set_stack(inv, "payment", 1, nil)
end
end
end
return false
end
mobs.trader_inventories = {}
function mobs.add_goods(entity, race)
local goods_to_add = nil
for i = 1, 15 do
if math.random(0, 100) > race.items[i][3] then
mobs.trader_inventory.set_stack(mobs.trader_inventory,
"goods", i, race.items[i][1])
end
end
end
function mobs_trader(self, clicker, entity, race)
local player = clicker:get_player_name()
if not self.id then
self.id = (math.random(1, 1000) * math.random(1, 10000))
.. self.npc_name .. (math.random(1, 1000) ^ 2)
end
if not self.game_name then
self.game_name = tostring(race.names[math.random(1, #race.names)])
self.npc_nametag = S("Trader @1", self.game_name)
self.object:set_properties({
nametag = self.npc_nametag,
nametag_color = "#00FF00"
})
end
local unique_entity_id = self.id
local is_inventory = minetest.get_inventory({
type = "detached", name = unique_entity_id})
local move_put_take = {
allow_move = mobs.allow_move,
allow_put = mobs.allow_put,
allow_take = mobs.allow_take,
on_move = function(inventory, from_list, from_index, to_list, to_index, count, player)
if from_list == "goods"
and to_list == "selection" then
local inv = inventory
local moved = inv.get_stack(inv,to_list, to_index)
local goodname = moved.get_name(moved)
local elements = moved.get_count(moved)
if elements > count then
-- remove the surplus parts
inv.set_stack(inv,"selection", 1,
goodname .. " " .. tostring(count))
-- the slot we took from is now free
inv.set_stack(inv,"goods",from_index,
goodname .. " " .. tostring(elements - count))
-- update the real amount of items in the slot now
elements = count
end
local good = nil
for i = 1, #race.items, 1 do
local stackstring = goodname .." " .. count
if race.items[i][1] == stackstring then
good = race.items[i]
end
end
if good ~= nil then
inventory.set_stack(inventory,"price", 1, good[2])
else
inventory.set_stack(inventory,"price", 1, nil)
end
mobs.update_takeaway(inv)
end
end,
on_put = mobs.on_put,
on_take = mobs.on_take
}
if is_inventory == nil then
mobs.trader_inventory = minetest.create_detached_inventory(unique_entity_id, move_put_take)
mobs.trader_inventory.set_size(mobs.trader_inventory,"goods", 15)
mobs.trader_inventory.set_size(mobs.trader_inventory,"takeaway", 1)
mobs.trader_inventory.set_size(mobs.trader_inventory,"selection", 1)
mobs.trader_inventory.set_size(mobs.trader_inventory,"price", 1)
mobs.trader_inventory.set_size(mobs.trader_inventory,"payment", 1)
mobs.add_goods(entity, race)
end
minetest.chat_send_player(player, S("[NPC] <Trader @1 > Hello, @2, have a look at my wares.",
self.game_name, player))
minetest.show_formspec(player, "trade", "size[8,10;]"
.. default.gui_bg_img
.. default.gui_slots
.. "label[0,0;" .. S("Trader @1's stock:", self.game_name) .. "]"
.. "list[detached:" .. unique_entity_id .. ";goods;.5,.5;3,5;]"
.. "label[4.5,0.5;" .. S("Selection") .. "]"
.. "list[detached:" .. unique_entity_id .. ";selection;4.5,1;5.5,2;]"
.. "label[6,0.5;" .. S("Price") .. "]"
.. "list[detached:" .. unique_entity_id .. ";price;6,1;7,2;]"
.. "label[4.5,3.5;" .. S("Payment") .. "]"
.. "list[detached:" .. unique_entity_id .. ";payment;4.5,4;5.5,5;]"
.. "label[6,3.5;" .. S("Bought items") .. "]"
.. "list[detached:" .. unique_entity_id .. ";takeaway;6,4;7.5,5.5;]"
.. "list[current_player;main;0,6;8,4;]"
)
end
mobs:register_egg("mobs_npc:trader", S("Trader"), "default_sandstone.png", 1)
-- compatibility
mobs:alias_mob("mobs:trader", "mobs_npc:trader")

View File

@ -1,264 +0,0 @@
if not minetest.get_modpath("shop") then
minetest.register_alias("shop:coin", "default:gold_ingot")
end
local S = mobs.intllib
mobs.human = {
items = {
-- item, price, chance
{"default:apple 10", "shop:coin 2", 40},
{"farming:bread 10", "shop:coin 4", 50},
{"default:clay 10", "shop:coin 2", 14},
{"default:brick 10", "shop:coin 4", 17},
{"default:glass 10", "shop:coin 4", 17},
{"default:obsidian 10", "shop:coin 15", 50},
{"default:diamond 1", "default:goldblock 1", 7},
{"default:goldblock 1", "default:diamond 1", 7},
{"farming:wheat 10", "shop:coin 2", 17},
{"default:tree 5", "shop:coin 4", 20},
{"default:stone 10", "shop:coin 8", 17},
{"default:desert_stone 10", "shop:coin 8", 27},
{"default:sapling 1", "shop:coin 1", 7},
{"default:pick_steel 1", "shop:coin 2", 7},
{"default:sword_steel 1", "shop:coin 2", 17},
{"default:shovel_steel 1", "shop:coin 1", 17},
},
names = {
"Bob", "Duncan", "Bill", "Tom", "James", "Ian", "Lenny"
}
}
-- Trader ( same as NPC but with right-click shop )
mobs:register_mob("mobs_npc:trader", {
type = "npc",
passive = false,
damage = 3,
attack_type = "dogfight",
attacks_monsters = true,
pathfinding = false,
hp_min = 10,
hp_max = 20,
armor = 100,
collisionbox = {-0.35,-1.0,-0.35, 0.35,0.8,0.35},
visual = "mesh",
mesh = "character.b3d",
textures = {
{"mobs_trader.png"}, -- by Frerin
{"mobs_trader2.png"}, -- re-coloured by amhadinger
{"mobs_trader3.png"}, -- re-coloured by amhadinger
},
makes_footstep_sound = true,
sounds = {},
walk_velocity = 2,
run_velocity = 3,
jump = false,
drops = {},
water_damage = 0,
lava_damage = 4,
light_damage = 0,
follow = {"default:diamond"},
view_range = 15,
owner = "",
order = "stand",
fear_height = 3,
animation = {
speed_normal = 30,
speed_run = 30,
stand_start = 0,
stand_end = 79,
walk_start = 168,
walk_end = 187,
run_start = 168,
run_end = 187,
punch_start = 200,
punch_end = 219,
},
on_rightclick = function(self, clicker)
mobs_trader(self, clicker, mobs.human)
end,
})
--This code comes almost exclusively from the trader and inventory of mobf, by Sapier.
--The copyright notice below is from mobf:
-------------------------------------------------------------------------------
-- Mob Framework Mod by Sapier
--
-- You may copy, use, modify or do nearly anything except removing this
-- copyright notice.
-- And of course you are NOT allow to pretend you have written it.
--
--! @file inventory.lua
--! @brief component containing mob inventory related functions
--! @copyright Sapier
--! @author Sapier
--! @date 2013-01-02
--
--! @defgroup Inventory Inventory subcomponent
--! @brief Component handling mob inventory
--! @ingroup framework_int
--! @{
--
-- Contact sapier a t gmx net
-------------------------------------------------------------------------------
-- Modifications Copyright 2016 by James Stevenson
local trader_inventory = {}
local function add_goods(race)
local goods_to_add = nil
for i = 1, 16 do
if math.random(0, 100) > race.items[i][3] then
trader_inventory.set_stack(trader_inventory,
"goods", i, race.items[i][1])
end
end
end
function mobs_trader(self, clicker, race)
local player = clicker:get_player_name()
if not self.id then
self.id = (math.random(1, 1000) * math.random(1, 10000))
.. self.npc_name .. (math.random(1, 1000) ^ 2)
end
if not self.game_name then
self.game_name = tostring(race.names[math.random(1, #race.names)])
self.npc_nametag = S("Trader @1", self.game_name)
self.object:set_properties({
nametag = self.npc_nametag,
nametag_color = "#00FF00"
})
end
local unique_entity_id = self.id
local is_inventory = minetest.get_inventory({
type = "detached", name = unique_entity_id})
local move_put_take = {
allow_move = function(inv, from_list, from_index, to_list, to_index, count, player)
if (from_list == "goods" and
to_list == "selection") or
(from_list == "selection" and
to_list == "goods") then
return count
else
return 0
end
end,
allow_put = function(inv, listname, index, stack, player)
return 0
end,
allow_take = function(inv, listname, index, stack, player)
return 0
end,
on_move = function(inv, from_list, from_index, to_list, to_index, count, player)
if from_list == "goods" and
to_list == "selection" then
local moved = inv.get_stack(inv, to_list, to_index)
local goodname = moved.get_name(moved)
local elements = moved.get_count(moved)
if elements > count then
-- Remove the surplus parts
inv.set_stack(inv, "selection", 1,
goodname .. " " .. tostring(count))
-- The slot we took from is now free.
inv.set_stack(inv, "goods", from_index,
goodname .. " " .. tostring(elements - count))
-- Update the real amount of items in the slot now.
elements = count
end
local good = nil
for i = 1, #race.items, 1 do
local stackstring = goodname .. " " .. count
if race.items[i][1] == stackstring then
good = race.items[i]
end
end
if good ~= nil then
inv.set_stack(inv, "price", 1, good[2])
else
inv.set_stack(inv, "price", 1, nil)
end
elseif from_list == "selection" and
to_list == "goods" then
inv.set_stack(inv, "price", 1, nil)
end
end,
on_put = function(inv, listname, index, stack, player)
end,
on_take = function(inv, listname, index, stack, player)
end,
}
if is_inventory == nil then
trader_inventory = minetest.create_detached_inventory(unique_entity_id, move_put_take)
trader_inventory.set_size(trader_inventory, "goods", 16)
trader_inventory.set_size(trader_inventory, "selection", 1)
trader_inventory.set_size(trader_inventory, "price", 1)
add_goods(race)
--print("added stuff")
end
minetest.chat_send_player(player, S("[NPC] <Trader @1> Hello, @2, have a look at my wares.",
self.game_name, player))
minetest.show_formspec(player, "mobs_npc:trader", "size[8,9]" ..
default.gui_bg ..
default.gui_bg_img ..
default.gui_slots ..
"list[detached:" .. unique_entity_id .. ";goods;0,0;8,2]" ..
"label[0,3;Selection]" ..
"list[detached:" .. unique_entity_id .. ";selection;2,3;1,1]" ..
"label[4,3;Price]" ..
"list[detached:" .. unique_entity_id .. ";price;6,3;1,1]" ..
"button[4,4;2,1;purchase;Purchase]" ..
"list[current_player;main;0,5;8,1;]" ..
"list[current_player;main;0,6.25;8,3;8]" ..
default.get_hotbar_bg(0, 5))
end
minetest.register_on_player_receive_fields(function(player, formname, fields)
if formname ~= "mobs_npc:trader" then
return
end
--print(dump(trader_inventory:get_lists()))
local selection_name = trader_inventory:get_stack("selection", 1):get_name()
local selection_count = trader_inventory:get_stack("selection", 1):get_count()
local selection_string = selection_name .. " " .. tostring(selection_count)
local price_name = trader_inventory:get_stack("price", 1):get_name()
local price_count = trader_inventory:get_stack("price", 1):get_count()
local price_string = price_name .. " " .. tostring(price_count)
--print(selection_string .. "\nfor:\n" .. price_string)
if player:get_inventory():contains_item("main", price_string) then
--print("you got it!")
trader_inventory:set_stack("selection", 1, nil)
trader_inventory:set_stack("price", 1, nil)
player:get_inventory():remove_item("main", price_string)
local adder = player:get_inventory():add_item("main", selection_string)
if adder then
minetest.add_item(player:getpos(), adder)
end
else
minetest.chat_send_player(player:get_player_name(),
"Not enough credits!")
end
end)
mobs:register_egg("mobs_npc:trader", S("Trader"), "default_sandstone.png", 1)
-- compatibility
mobs:alias_mob("mobs:trader", "mobs_npc:trader")