Ir para conteúdo
Banner com Efeitos

Featured Replies

Postado

Alguém poderia me ajudar com o meu npc Gnomally ? Quando falo items, ( ou o nome de qualquer item ), e relations, ele fica mudo e da erro no console ://

 

local keywordHandler = KeywordHandler:new()

local npcHandler = NpcHandler:new(keywordHandler)
NpcSystem.parseParameters(npcHandler)

function onCreatureAppear(cid) npcHandler:onCreatureAppear(cid) end
function onCreatureDisappear(cid) npcHandler:onCreatureDisappear(cid) end
function onCreatureSay(cid, type, msg) npcHandler:onCreatureSay(cid, type, msg) end
function onThink() npcHandler:onThink() end

local config, t, renown = {
['supply'] = {itemid = 18215, token = {type = 'minor', id = 18422, count = 2}},
['muck'] = {itemid = 18395, token = {type = 'minor', id = 18422, count = 8}},
['mission'] = {itemid = 18509, token = {type = 'minor', id = 18422, count = 10}},
['lamp'] = {itemid = 18388, token = {type = 'minor', id = 18422, count = 15}},
['backpack'] = {itemid = 18393, token = {type = 'minor', id = 18422, count = 15}},
['addition to the soil guardian outfit'] = {itemid = 18518, token = {type = 'minor', id = 18422, count = 70}},
['addition to the crystal warlord armor outfit'] = {itemid = 18521, token = {type = 'minor', id = 18422, count = 70}},
['gill gugel'] = {itemid = 18398, token = {type = 'major', id = 18423, count = 10}},
['gill coat'] = {itemid = 18399, token = {type = 'major', id = 18423, count = 10}},
['gill legs'] = {itemid = 18400, token = {type = 'major', id = 18423, count = 10}},
['spellbook'] = {itemid = 18401, token = {type = 'major', id = 18423, count = 10}},
['prismatic helmet'] = {itemid = 18403, token = {type = 'major', id = 18423, count = 10}},
['prismatic armor'] = {itemid = 18404, token = {type = 'major', id = 18423, count = 10}},
['prismatic legs'] = {itemid = 18405, token = {type = 'major', id = 18423, count = 10}},
['prismatic boots'] = {itemid = 18406, token = {type = 'major', id = 18423, count = 10}},
['prismatic shield'] = {itemid = 18410, token = {type = 'major', id = 18423, count = 10}},
['basic soil guardian outfit'] = {itemid = 18517, token = {type = 'major', id = 18423, count = 20}},
['basic crystal warlord outfit'] = {itemid = 18520, token = {type = 'major', id = 18423, count = 20}},
['iron loadstone'] = {itemid = 18447, token = {type = 'major', id = 18423, count = 20}},
['glow wine'] = {itemid = 18448, token = {type = 'major', id = 18423, count = 20}}
}, {}, {}

local function getTable()
local itemsList = {
  {name = "bell", id = 18343, buy = 50},
  {name = "gnomish crystal package", id = 18313, buy = 1000},
  {name = "gnomish extraction crystal", id = 18213, buy = 50},
  {name = "gnomish spore gatherer", id = 18328, buy = 50},
  {name = "little pig", id = 18339, buy = 150}
}
return itemsList
end

local function setNewTradeTable(table)
local items = {}
for _, v in ipairs(table) do
  items[v.id] = {itemId = v.id, buyPrice = v.buy, sellPrice = v.sell, subType = 0, realName = v.name}
end
return items
end

local function onBuy(cid, item, subType, amount, ignoreCap, inBackpacks)
local player = Player(cid)
local items = setNewTradeTable(getTable())
local count = 0
for i = 1, amount do
  local item = Game.createItem(items[item].itemId, subType)
  if player:addItemEx(item, false) ~= RETURNVALUE_NOERROR then
   npcHandler:say('First make sure you have enough space in your inventory.', cid)
   break
  end
  count = i
end

if count == 0 then
  return true
end

player:removeMoney(items[item].buyPrice * count)
player:sendTextMessage(MESSAGE_INFO_DESCR, string.format('Bought %dx %s for %d gold.', count, items[item].realName, items[item].buyPrice * count))
return true
end

local function getTokenCount(s)
local b, e = s:find("%d+")
return b and e and math.min(4294967295, tonumber(s:sub(b, e))) or -1
end

local function greetCallback(cid)
npcHandler:setMessage(MESSAGE_GREET, 'Oh, hello! I\'m the gnome-human relations assistant. I am here for you to trade your tokens for {equipment}, resupply you with mission {items} and talk to you about your {relations} to us gnomes! ...')
t[cid], renown[cid] = nil, nil
return true
end

local function creatureSayCallback(cid, type, msg)
if not npcHandler:isFocused(cid) then
  return false
end

if msgcontains(msg, 'equipment') then
  npcHandler:say('You can buy different equipment for minor or for major tokens. So, which is the equipment you are interested in, the one for {minor} or {major} tokens? ...', cid)
elseif msgcontains(msg, 'major') then
  npcHandler:say('For ten major tokens, I can offer you a {gill gugel}, a {gill coat}, {gill legs}, a {spellbook} of vigilance, a {prismatic helmet}, a {prismatic armor}, {prismatic legs}, {prismatic boots} or a {prismatic shield} ...', cid)
elseif msgcontains(msg, 'minor') then
  npcHandler:say('For two minor tokens, you can buy one gnomish {supply} package! For eight tokens, you can buy a {muck} remover! For ten tokens, you can buy a {mission} crystal. For fifteen tokens, you can buy a crystal {lamp} or a mushroom {backpack}... For seventy tokens, I can offer you a voucher for an {addition to the soil guardian outfit}, or a voucher for an {addition to the crystal warlord armor outfit}.', cid)
elseif config[msg] then
  local itemType = ItemType(config[msg]['itemid'])
  npcHandler:say(string.format('Do you want to trade %s %s for %d %s tokens?', (itemType:getArticle() ~= "" and itemType:getArticle() or ""), itemType:getName(), config[msg]['token']['count'], config[msg]['token']['type']), cid)
  npcHandler.topic[cid] = 1
  t[cid] = msg
elseif msgcontains(msg, 'relations') then
  npcHandler:say('Your renown amongst us gnomes is currently {' .. math.max(0, player:getStorageValue(921)) .. '}. Do you want to improve your standing by sacrificing tokens? One token will raise your renown by 5 points. ', cid)
  local player = Player(cid)
  if player:getStorageValue(900) >= 14 then
  npcHandler:say('Our relations improve with every mission you undertake on our behalf. Another way to improve your relations with us gnomes is to trade in minor crystal tokens. ...', cid)
  npcHandler:say('Your renown amongst us gnomes is currently {' .. math.max(0, player:getStorageValue(921)) .. '}. Do you want to improve your standing by sacrificing tokens? One token will raise your renown by 5 points. ', cid)
  npcHandler.topic[cid] = 2
  else
   npcHandler:say('You are not even a recruit of the Bigfoots. Sorry I can\'t help you.', cid)
  end
elseif npcHandler.topic[cid] == 3 then
  local amount = getTokenCount(msg)
  if amount > 0 then
   npcHandler:say('Do you really want to trade ' .. amount .. ' minor tokens for ' .. amount * 5 .. ' renown?', cid)
   renown[cid] = amount
   npcHandler.topic[cid] = 4
  end
elseif msgcontains(msg, 'items') then
  npcHandler:say('Do you need to buy any mission items?', cid)
  npcHandler.topic[cid] = 5
elseif msgcontains(msg, 'yes') then
  if npcHandler.topic[cid] == 1 then
   local player, targetTable = Player(cid), config[t[cid]]
   if player:getItemCount(targetTable['token']['id']) < targetTable['token']['count'] then
    npcHandler:say('Sorry, you don\'t have enough ' .. targetTable['token']['type'] .. ' tokens with you.', cid)
    npcHandler.topic[cid] = 0
    return true
   end

   local item = Game.createItem(targetTable['itemid'], 1)
   local weight = 0
   weight = ItemType(item:getId()):getWeight(item:getCount())

   if player:addItemEx(item) ~= RETURNVALUE_NOERROR then
    if player:getFreeCapacity() < weight then
     npcHandler:say('First make sure you have enough capacity to hold it.', cid)
    else
     npcHandler:say('First make sure you have enough space in your inventory.', cid)
    end
    npcHandler.topic[cid] = 0
    return true
   end

   player:removeItem(targetTable['token']['id'], targetTable['token']['count'])
   npcHandler:say('Here have one of our ' .. item:getPluralName() .. '.', cid)
   npcHandler.topic[cid] = 0
  elseif npcHandler.topic[cid] == 2 then
   npcHandler:say("How many tokens do you want to trade?", cid)
   npcHandler.topic[cid] = 3
  elseif npcHandler.topic[cid] == 4 then
   local player = Player(cid)
   if player:getItemCount(18422) >= renown[cid] then
    player:removeItem(18422, renown[cid])
    player:setStorageValue(921, math.max(0, player:getStorageValue(921)) + renown[cid] * 5)
    npcHandler:say('As you wish! Your new renown is {' .. player:getStorageValue(921) .. '}.', cid)
   else
    npcHandler:say('You don\'t have these many tokens.', cid)
   end
   npcHandler.topic[cid] = 0
  elseif npcHandler.topic[cid] == 5 then
   openShopWindow(cid, getTable(), onBuy, onSell)
   npcHandler:say('Let us see if I have what you need.', cid)
   npcHandler.topic[cid] = 0
  end
elseif msgcontains(msg, 'no') and isInArray(1, 3, 4, 5, npcHandler.topic[cid]) then
  npcHandler:say('As you like.', cid)
  npcHandler.topic[cid] = 0
end
return true
end

npcHandler:setCallback(CALLBACK_GREET, greetCallback)
npcHandler:setCallback(CALLBACK_MESSAGE_DEFAULT, creatureSayCallback)

npcHandler:addModule(FocusModule:new())

-- data\npc\scripts\gnomally

 

if(NpcHandler == nil) then
-- Constant talkdelay behaviors.
TALKDELAY_NONE = 0 -- No talkdelay. Npc will reply immedeatly.
TALKDELAY_ONTHINK = 1 -- Talkdelay handled through the onThink callback function. (Default)
TALKDELAY_EVENT = 2 -- Not yet implemented

-- Currently applied talkdelay behavior. TALKDELAY_ONTHINK is default.
NPCHANDLER_TALKDELAY = TALKDELAY_ONTHINK

-- Constant conversation behaviors.
CONVERSATION_DEFAULT = 0 -- Conversation through default window, like it was before 8.2 update.
CONVERSATION_PRIVATE = 1 -- Conversation through NPCs chat window, as of 8.2 update. (Default)
  --Small Note: Private conversations also means the NPC will use multi-focus system.

-- Currently applied conversation behavior. CONVERSATION_PRIVATE is default.
NPCHANDLER_CONVBEHAVIOR = CONVERSATION_PRIVATE

-- Constant indexes for defining default messages.
MESSAGE_GREET    = 1 -- When the player greets the npc.
MESSAGE_FAREWELL   = 2 -- When the player unGreets the npc.
MESSAGE_BUY    = 3 -- When the npc asks the player if he wants to buy something.
MESSAGE_ONBUY    = 4 -- When the player successfully buys something via talk.
MESSAGE_BOUGHT   = 5 -- When the player bought something through the shop window.
MESSAGE_SELL    = 6 -- When the npc asks the player if he wants to sell something.
MESSAGE_ONSELL    = 7 -- When the player successfully sells something via talk.
MESSAGE_SOLD   = 8 -- When the player sold something through the shop window.
MESSAGE_MISSINGMONEY  = 9 -- When the player does not have enough money.
MESSAGE_MISSINGITEM  = 10 -- When the player is trying to sell an item he does not have.
MESSAGE_NEEDMONEY  = 11 -- Same as above, used for shop window.
MESSAGE_NEEDITEM  = 12 -- Same as above, used for shop window.
MESSAGE_NEEDSPACE   = 13 -- When the player don't have any space to buy an item
MESSAGE_NEEDMORESPACE  = 14 -- When the player has some space to buy an item, but not enough space
MESSAGE_IDLETIMEOUT  = 15 -- When the player has been idle for longer then idleTime allows.
MESSAGE_WALKAWAY  = 16 -- When the player walks out of the talkRadius of the npc.
MESSAGE_DECLINE   = 17 -- When the player says no to something.
MESSAGE_SENDTRADE  = 18 -- When the npc sends the trade window to the player
MESSAGE_NOSHOP   = 19 -- When the npc's shop is requested but he doesn't have any
MESSAGE_ONCLOSESHOP  = 20 -- When the player closes the npc's shop window
MESSAGE_ALREADYFOCUSED  = 21 -- When the player already has the focus of this npc.
MESSAGE_PLACEDINQUEUE  = 22 -- When the player has been placed in the costumer queue.

-- Constant indexes for callback functions. These are also used for module callback ids.
CALLBACK_CREATURE_APPEAR  = 1
CALLBACK_CREATURE_DISAPPEAR = 2
CALLBACK_CREATURE_SAY   = 3
CALLBACK_ONTHINK   = 4
CALLBACK_GREET    = 5
CALLBACK_FAREWELL   = 6
CALLBACK_MESSAGE_DEFAULT  = 7
CALLBACK_PLAYER_ENDTRADE  = 8
CALLBACK_PLAYER_CLOSECHANNEL = 9
CALLBACK_ONBUY   = 10
CALLBACK_ONSELL   = 11

-- Addidional module callback ids
CALLBACK_MODULE_INIT  = 12
CALLBACK_MODULE_RESET  = 13

-- Constant strings defining the keywords to replace in the default messages.
TAG_PLAYERNAME = '|PLAYERNAME|'
TAG_ITEMCOUNT = '|ITEMCOUNT|'
TAG_TOTALCOST = '|TOTALCOST|'
TAG_ITEMNAME = '|ITEMNAME|'
TAG_QUEUESIZE = '|QUEUESIZE|'

NpcHandler = {
  keywordHandler = nil,
  focuses = nil,
  talkStart = nil,
  idleTime = 300,
  talkRadius = 3,
  talkDelayTime = 350, -- Seconds to delay outgoing messages.
  queue = nil,
  talkDelay = nil,
  callbackFunctions = nil,
  modules = nil,
  shopItems = nil, -- They must be here since ShopModule uses "static" functions
  messages = {
   -- These are the default replies of all npcs. They can/should be changed individually for each npc.
   [MESSAGE_GREET]  = 'Bem Vindo, {|PLAYERNAME|}! Tenho estado a sua espera.',
   [MESSAGE_FAREWELL]  = 'Tchau, Tchau, {|PLAYERNAME|}!',
   [MESSAGE_BUY]   = 'Você quer comprar |ITEMCOUNT| |ITEMNAME| por |TOTALCOST| gold coins?',
   [MESSAGE_ONBUY]  = 'Foi um prazer fazer negocio com você.',
   [MESSAGE_BOUGHT]  = 'Comprado |ITEMCOUNT|x |ITEMNAME| por |TOTALCOST| gold.',
   [MESSAGE_SELL]   = 'Você quer vender |ITEMCOUNT| |ITEMNAME| por |TOTALCOST| gold coins?',
   [MESSAGE_ONSELL]  = 'Obrigado por este |ITEMNAME|, |PLAYERNAME|.',
   [MESSAGE_SOLD]   = 'Vendido |ITEMCOUNT|x |ITEMNAME| por |TOTALCOST| gold.',
   [MESSAGE_MISSINGMONEY] = 'Desculpe, você não tem dinheiro suficiente.',
   [MESSAGE_MISSINGITEM]  = 'Você nem sequer tem esse item, |PLAYERNAME|!',
   [MESSAGE_NEEDMONEY]  = 'Você não tem dinheiro suficiente.',
   [MESSAGE_NEEDITEM] = 'Você não tem esse objeto.',
   [MESSAGE_NEEDSPACE] = 'Você não tem capacidade suficiente.',
   [MESSAGE_NEEDMORESPACE] = 'Você não tem capacidade suficiente para todos os itens.',
   [MESSAGE_IDLETIMEOUT]  = 'Próximo, por favor!!',
   [MESSAGE_WALKAWAY]  = 'Pelo menos um Tchau ne, Ingrato!',
   [MESSAGE_DECLINE] = 'Não tá bom o suficiente, não tá? ...?',
   [MESSAGE_SENDTRADE] = 'Aqui está a minha oferta, {|PLAYERNAME|}.',
   [MESSAGE_NOSHOP] = 'Desculpe, eu não estou oferecendo nada.',
   [MESSAGE_ONCLOSESHOP] = 'Obrigado, volte quando você quiser mais coisas.',
   [MESSAGE_ALREADYFOCUSED]= '|PLAYERNAME|! Eu ja estou falando com você ...',
   [MESSAGE_PLACEDINQUEUE] = '|PLAYERNAME|, por favor, aguarde a sua vez. Há |QUEUESIZE| clientes antes de você.'
  }
}

-- Creates a new NpcHandler with an empty callbackFunction stack.
function NpcHandler:new(keywordHandler)
  local obj = {}
  obj.messages = {}

  obj.keywordHandler = keywordHandler
  if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
   obj.focuses = {}
   obj.talkStart = {}
  else
   obj.queue = Queue:new(obj)
   obj.focuses = 0
   obj.talkStart = 0
  end

  obj.callbackFunctions = {}
  obj.modules = {}
  obj.talkDelay = {}
  obj.shopItems = {}

  setmetatable(obj.messages, self.messages)
  self.messages.__index = self.messages

  setmetatable(obj, self)
  self.__index = self
  return obj
end

-- Re-defines the maximum idle time allowed for a player when talking to this npc.
function NpcHandler:setMaxIdleTime(newTime)
  self.idleTime = newTime
end

-- Attackes a new keyword handler to this npchandler
function NpcHandler:setKeywordHandler(newHandler)
  self.keywordHandler = newHandler
end

-- Function used to change the focus of this npc.
function NpcHandler:addFocus(newFocus)
  if(not isCreature(newFocus)) then
   return
  end

  if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
   if(self:isFocused(newFocus, true)) then
    return
   end

   table.insert(self.focuses, newFocus)
  else
   self.focuses = newFocus
  end

  self:updateFocus(true)
end
NpcHandler.changeFocus = NpcHandler.addFocus -- "changeFocus" looks better for CONVERSATION_DEFAULT

-- Function used to verify if npc is focused to certain player
function NpcHandler:isFocused(focus, creatureCheck)
  local creatureCheck = creatureCheck or false
  if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
   for k, v in pairs(self.focuses) do
    if(v == focus) then
     if(creatureCheck or isCreature(v)) then
      return true
     end

     self:unsetFocus(focus, k)
     return false
    end
   end

   return false
  end

  if(creatureCheck or isCreature(self.focuses)) then
   return self.focuses == focus
  end

  self:changeFocus(0)
  return false
end

-- This function should be called on each onThink and makes sure the npc faces the player it is talking to.
-- Should also be called whenever a new player is focused.
function NpcHandler:updateFocus(creatureCheck)
  local creatureCheck = creatureCheck or false
  if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
   for _, focus in pairs(self.focuses) do
    if(creatureCheck or isCreature(focus)) then
     doNpcSetCreatureFocus(focus)
     return
    end
   end
  elseif(creatureCheck or isCreature(self.focuses)) then
   doNpcSetCreatureFocus(self.focuses)
   return
  end

  doNpcSetCreatureFocus(0)
end

-- Used when the npc should un-focus the player.
function NpcHandler:releaseFocus(focus)
  if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
   if(not self:isFocused(focus)) then
    return
   end

   local pos = nil
   for k, v in pairs(self.focuses) do
    if(v == focus) then
     pos = k
    end
   end

   if(pos ~= nil) then
    closeShopWindow(focus)
    self:unsetFocus(focus, pos)
   end
  elseif(self.focuses == focus) then
   if(isCreature(focus)) then
    closeShopWindow(focus)
   end

   self:changeFocus(0)
  end
end

-- Internal un-focusing function, beware using!
function NpcHandler:unsetFocus(focus, pos)
  if(type(self.focuses) ~= "table" or pos == nil or self.focuses[pos] == nil) then
   return
  end

  table.remove(self.focuses, pos)
  self.talkStart[focus] = nil
  self:updateFocus()
end

-- Returns the callback function with the specified id or nil if no such callback function exists.
function NpcHandler:getCallback(id)
  local ret = nil
  if(self.callbackFunctions ~= nil) then
   ret = self.callbackFunctions[id]
  end

  return ret
end

-- Changes the callback function for the given id to callback.
function NpcHandler:setCallback(id, callback)
  if(self.callbackFunctions ~= nil) then
   self.callbackFunctions[id] = callback
  end
end

-- Adds a module to this npchandler and inits it.
function NpcHandler:addModule(module)
  if(self.modules == nil or module == nil) then
   return false
  end

  module:init(self)
  if(module.parseParameters ~= nil) then
   module:parseParameters()
  end

  table.insert(self.modules, module)
  return true
end

-- Calls the callback function represented by id for all modules added to this npchandler with the given arguments.
function NpcHandler:processModuleCallback(id, ...)
  local ret = true
  for _, module in pairs(self.modules) do
   local tmpRet = true
   if(id == CALLBACK_CREATURE_APPEAR and module.callbackOnCreatureAppear ~= nil) then
    tmpRet = module:callbackOnCreatureAppear(...)
   elseif(id == CALLBACK_CREATURE_DISAPPEAR and module.callbackOnCreatureDisappear ~= nil) then
    tmpRet = module:callbackOnCreatureDisappear(...)
   elseif(id == CALLBACK_CREATURE_SAY and module.callbackOnCreatureSay ~= nil) then
    tmpRet = module:callbackOnCreatureSay(...)
   elseif(id == CALLBACK_PLAYER_ENDTRADE and module.callbackOnPlayerEndTrade ~= nil) then
    tmpRet = module:callbackOnPlayerEndTrade(...)
   elseif(id == CALLBACK_PLAYER_CLOSECHANNEL and module.callbackOnPlayerCloseChannel ~= nil) then
    tmpRet = module:callbackOnPlayerCloseChannel(...)
   elseif(id == CALLBACK_ONBUY and module.callbackOnBuy ~= nil) then
    tmpRet = module:callbackOnBuy(...)
   elseif(id == CALLBACK_ONSELL and module.callbackOnSell ~= nil) then
    tmpRet = module:callbackOnSell(...)
   elseif(id == CALLBACK_ONTHINK and module.callbackOnThink ~= nil) then
    tmpRet = module:callbackOnThink(...)
   elseif(id == CALLBACK_GREET and module.callbackOnGreet ~= nil) then
    tmpRet = module:callbackOnGreet(...)
   elseif(id == CALLBACK_FAREWELL and module.callbackOnFarewell ~= nil) then
    tmpRet = module:callbackOnFarewell(...)
   elseif(id == CALLBACK_MESSAGE_DEFAULT and module.callbackOnMessageDefault ~= nil) then
    tmpRet = module:callbackOnMessageDefault(...)
   elseif(id == CALLBACK_MODULE_RESET and module.callbackOnModuleReset ~= nil) then
    tmpRet = module:callbackOnModuleReset(...)
   end

   if(not tmpRet) then
    ret = false
    break
   end
  end

  return ret
end

-- Returns the message represented by id.
function NpcHandler:getMessage(id)
  local ret = nil
  if(self.messages ~= nil) then
   ret = self.messages[id]
  end

  return ret
end

-- Changes the default response message with the specified id to newMessage.
function NpcHandler:setMessage(id, newMessage)
  if(self.messages ~= nil) then
   self.messages[id] = newMessage
  end
end

-- Translates all message tags found in msg using parseInfo
function NpcHandler:parseMessage(msg, parseInfo)
  for search, replace in pairs(parseInfo) do
   if(replace ~= nil) then
    msg = msg:gsub(search, replace)
   end
  end

  return msg
end

-- Makes sure the npc un-focuses the currently focused player
function NpcHandler:unGreet(cid)
  if(not self:isFocused(cid)) then
   return
  end

  local callback = self:getCallback(CALLBACK_FAREWELL)
  if(callback == nil or callback(cid)) then
   if(self:processModuleCallback(CALLBACK_FAREWELL)) then
    if(self.queue == nil or not self.queue:greetNext()) then
     local msg = self:getMessage(MESSAGE_FAREWELL)
     msg = self:parseMessage(msg, { [TAG_PLAYERNAME] = getPlayerName(cid) or -1 })

     self:resetNpc(cid)
     if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
      self:say(msg, cid, 0, true)
      msg = msg:gsub('{', ''):gsub('}', '')
      local ghost, position = isPlayerGhost(cid), getThingPosition(getNpcId())

      local spectators, nid = getSpectators(position, 7, 7), getNpcId()
      for _, pid in ipairs(spectators) do
       if(isPlayer(pid) and pid ~= cid) then
        if(NPCHANDLER_TALKDELAY ~= TALKDELAY_NONE) then
         addEvent(doCreatureSay, self.talkDelayTime, nid, msg, TALKTYPE_SAY, ghost, pid, position)
        else
         doCreatureSay(nid, msg, TALKTYPE_SAY, ghost, pid, position)
        end
       end
      end
     else
      self:say(msg)
     end

     self:releaseFocus(cid)
    end
   end
  end
end

-- Greets a new player.
function NpcHandler:greet(cid)
  local callback = self:getCallback(CALLBACK_GREET)
  if(callback == nil or callback(cid)) then
   if(self:processModuleCallback(CALLBACK_GREET, cid)) then
    local msg = self:getMessage(MESSAGE_GREET)
    msg = self:parseMessage(msg, { [TAG_PLAYERNAME] = getCreatureName(cid) })

    self:addFocus(cid)
    if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
     self:say(msg, cid, 0, true)
     msg = msg:gsub('{', ''):gsub('}', '')
     local ghost, position = isPlayerGhost(cid), getThingPosition(getNpcId())

     local spectators, nid = getSpectators(position, 7, 7), getNpcId()
     for _, pid in ipairs(spectators) do
      if(isPlayer(pid) and pid ~= cid) then
       if(NPCHANDLER_TALKDELAY ~= TALKDELAY_NONE) then
        addEvent(doCreatureSay, self.talkDelayTime, nid, msg, TALKTYPE_SAY, ghost, pid, position)
       else
        doCreatureSay(nid, msg, TALKTYPE_SAY, ghost, pid, position)
       end
      end
     end
    else
     self:say(msg)
    end
   end
  end
end

-- Handles onCreatureAppear events. If you with to handle this yourself, please use the CALLBACK_CREATURE_APPEAR callback.
function NpcHandler:onCreatureAppear(cid)
  local callback = self:getCallback(CALLBACK_CREATURE_APPEAR)
  if(callback == nil or callback(cid)) then
   if(self:processModuleCallback(CALLBACK_CREATURE_APPEAR, cid)) then
    --
   end
  end
end

-- Handles onCreatureDisappear events. If you with to handle this yourself, please use the CALLBACK_CREATURE_DISAPPEAR callback.
function NpcHandler:onCreatureDisappear(cid)
  local callback = self:getCallback(CALLBACK_CREATURE_DISAPPEAR)
  if(callback == nil or callback(cid)) then
   if(self:processModuleCallback(CALLBACK_CREATURE_DISAPPEAR, cid)) then
    if(self:isFocused(cid)) then
     self:unGreet(cid)
    end
   end
  end
end

-- Handles onCreatureSay events. If you with to handle this yourself, please use the CALLBACK_CREATURE_SAY callback.
function NpcHandler:onCreatureSay(cid, class, msg)
  local callback = self:getCallback(CALLBACK_CREATURE_SAY)
  if(callback == nil or callback(cid, class, msg)) then
   if(self:processModuleCallback(CALLBACK_CREATURE_SAY, cid, class, msg)) then
    if(not self:isInRange(cid)) then
     return
    end

    if(self.keywordHandler ~= nil) then
     if((self:isFocused(cid) and (class == TALKTYPE_PRIVATE_PN or NPCHANDLER_CONVBEHAVIOR == CONVERSATION_DEFAULT)) or not self:isFocused(cid)) then
      local ret = self.keywordHandler:processMessage(cid, msg)
      if(not ret) then
       local callback = self:getCallback(CALLBACK_MESSAGE_DEFAULT)
       if(callback ~= nil and callback(cid, class, msg)) then
        if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
         self.talkStart[cid] = os.time()
        else
         self.talkStart = os.time()
        end
       end
      elseif(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
       self.talkStart[cid] = os.time()
      else
       self.talkStart = os.time()
      end
     end
    end
   end
  end
end

-- Handles onPlayerEndTrade events. If you wish to handle this yourself, use the CALLBACK_PLAYER_ENDTRADE callback.
function NpcHandler:onPlayerEndTrade(cid)
  local callback = self:getCallback(CALLBACK_PLAYER_ENDTRADE)
  if(callback == nil or callback(cid)) then
   if(self:processModuleCallback(CALLBACK_PLAYER_ENDTRADE, cid)) then
    if(self:isFocused(cid)) then
     local parseInfo = { [TAG_PLAYERNAME] = getPlayerName(cid) }
     local msg = self:parseMessage(self:getMessage(MESSAGE_ONCLOSESHOP), parseInfo)
     self:say(msg, cid)
    end
   end
  end
end

-- Handles onPlayerCloseChannel events. If you wish to handle this yourself, use the CALLBACK_PLAYER_CLOSECHANNEL callback.
function NpcHandler:onPlayerCloseChannel(cid)
  local callback = self:getCallback(CALLBACK_PLAYER_CLOSECHANNEL)
  if(callback == nil or callback(cid)) then
   if(self:processModuleCallback(CALLBACK_PLAYER_CLOSECHANNEL, cid)) then
    if(self:isFocused(cid)) then
     self:unGreet(cid)
    end
   end
  end
end

-- Handles onBuy events. If you wish to handle this yourself, use the CALLBACK_ONBUY callback.
function NpcHandler:onBuy(cid, itemid, subType, amount, ignoreCap, inBackpacks)
  local callback = self:getCallback(CALLBACK_ONBUY)
  if(callback == nil or callback(cid, itemid, subType, amount, ignoreCap, inBackpacks)) then
   if(self:processModuleCallback(CALLBACK_ONBUY, cid, itemid, subType, amount, ignoreCap, inBackpacks)) then
    --
   end
  end
end

-- Handles onSell events. If you wish to handle this yourself, use the CALLBACK_ONSELL callback.
function NpcHandler:onSell(cid, itemid, subType, amount, ignoreCap, inBackpacks)
  local callback = self:getCallback(CALLBACK_ONSELL)
  if(callback == nil or callback(cid, itemid, subType, amount, ignoreCap, inBackpacks)) then
   if(self:processModuleCallback(CALLBACK_ONSELL, cid, itemid, subType, amount, ignoreCap, inBackpacks)) then
    --
   end
  end
end

-- Handles onThink events. If you wish to handle this yourself, please use the CALLBACK_ONTHINK callback.
function NpcHandler:onThink()
  local callback = self:getCallback(CALLBACK_ONTHINK)
  if(callback == nil or callback()) then
   for i, speech in pairs(self.talkDelay) do
    if((speech.cid == nil or speech.cid == 0) and speech.time ~= nil and speech.message ~= nil) then
     if(os.mtime() >= speech.time) then
      selfSay(speech.message)
      self.talkDelay = nil
     end
    elseif(isCreature(speech.cid) and speech.start ~= nil and speech.time ~= nil and speech.message ~= nil) then
     if(os.mtime() >= speech.time) then
      local talkStart = (NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT and self.talkStart[speech.cid] or self.talkStart)
      if(speech.force or (self:isFocused(speech.cid) and talkStart == speech.start)) then
       if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
        selfSay(speech.message, speech.cid)
       else
        selfSay(speech.message)
       end
      end

      self.talkDelay = nil
     end
    else
     self.talkDelay = nil
    end
   end

   if(self:processModuleCallback(CALLBACK_ONTHINK)) then
    if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
     for _, focus in pairs(self.focuses) do
      if(focus ~= nil) then
       if(not self:isInRange(focus)) then
        self:onWalkAway(focus)
       elseif((os.time() - self.talkStart[focus]) > self.idleTime) then
        self:unGreet(focus)
       else
        self:updateFocus()
       end
      end
     end
    elseif(self.focuses ~= 0) then
     if(not self:isInRange(self.focuses)) then
      self:onWalkAway(self.focuses)
     elseif((os.time() - self.talkStart) > self.idleTime) then
      self:unGreet(self.focuses)
     else
      self:updateFocus()
     end
    end
   end
  end
end

-- Tries to greet the player with the given cid.
function NpcHandler:onGreet(cid)
  if(self:isInRange(cid)) then
   if(NPCHANDLER_CONVBEHAVIOR == CONVERSATION_PRIVATE) then
    if(not self:isFocused(cid)) then
     self:greet(cid)
     return
    end
   elseif(NPCHANDLER_CONVBEHAVIOR == CONVERSATION_DEFAULT) then
    if(self.focuses == 0) then
     self:greet(cid)
    elseif(self.focuses == cid) then
     local msg = self:getMessage(MESSAGE_ALREADYFOCUSED)
     local parseInfo = { [TAG_PLAYERNAME] = getCreatureName(cid) }
     msg = self:parseMessage(msg, parseInfo)
     self:say(msg)
    else
     if(not self.queue:isInQueue(cid)) then
      self.queue:push(cid)
     end

     local msg = self:getMessage(MESSAGE_PLACEDINQUEUE)
     local parseInfo = { [TAG_PLAYERNAME] = getCreatureName(cid), [TAG_QUEUESIZE] = self.queue:getSize() }
     msg = self:parseMessage(msg, parseInfo)
     self:say(msg)
    end
   end
  end
end

-- Simply calls the underlying unGreet function.
function NpcHandler:onFarewell(cid)
  self:unGreet(cid)
end

-- Should be called on this npc's focus if the distance to focus is greater then talkRadius.
function NpcHandler:onWalkAway(cid)
  if(self:isFocused(cid)) then
   local callback = self:getCallback(CALLBACK_CREATURE_DISAPPEAR)
   if(callback == nil or callback(cid)) then
    if(self:processModuleCallback(CALLBACK_CREATURE_DISAPPEAR, cid)) then
     if(self.queue == nil or not self.queue:greetNext()) then
      local msg = self:getMessage(MESSAGE_WALKAWAY)
      self:say(msg, cid, 0, false)
      self:releaseFocus(cid)
     end
    end
   end
  end
end

-- Returns true if cid is within the talkRadius of this npc.
function NpcHandler:isInRange(cid)
  if not isPlayer(cid) then
   return false
  end

  local distance = getNpcDistanceTo(cid) or -1
  return distance ~= -1 and distance <= self.talkRadius
end

-- Resets the npc into it's initial state (in regard of the keyrodhandler).
-- All modules are also receiving a reset call through their callbackOnModuleReset function.
function NpcHandler:resetNpc(cid)
  if(self:processModuleCallback(CALLBACK_MODULE_RESET)) then
   self.keywordHandler:reset(cid)
  end
end

-- Makes the npc represented by this instance of NpcHandler say something.
-- This implements the currently set type of talkdelay.
function NpcHandler:say(message, focus, delay, force)
  local delay = delay or 0
  if(NPCHANDLER_TALKDELAY == TALKDELAY_NONE or delay <= 0) then
   if(NPCHANDLER_CONVBEHAVIOR ~= CONVERSATION_DEFAULT) then
    selfSay(message, focus)
   else
    selfSay(message)
   end

   return
  end

  -- TODO: Add an event handling method for delayed messages
  table.insert(self.talkDelay, {
   id = getNpcId(),
   cid = focus,
   message = message,
   time = os.mtime() + (delay and delay or self.talkDelayTime),
   start = os.time(),
   force = force or false
  })
end

end

-- data\npc\lib\npcsystem

 

10336759_287648988091760_734166607993481

Editado por AlekysRocha. (veja o histórico de edições)

Participe da conversa

Você pode postar agora e se cadastrar mais tarde. Se você tem uma conta, faça o login para postar com sua conta.

Visitante
Responder

Quem Está Navegando 0

  • Nenhum usuário registrado visualizando esta página.

Estatísticas dos Fóruns

  • Tópicos 96.9k
  • Posts 519.7k

Informação Importante

Confirmação de Termo