• There is NO official Otland's Discord server and NO official Otland's server list. The Otland's Staff does not manage any Discord server or server list. Moderators or administrator of any Discord server or server lists have NO connection to the Otland's Staff. Do not get scammed!

TFS 1.X+ attempt to call method 'outfit' (a nil value)

SixNine

Active Member
Joined
Dec 12, 2018
Messages
469
Reaction score
44
LUA:
function onKill(player, target)
  if not target or target:isPlayer() or target:getMaster() then
    return true
  end

  local taskId = Cache.Tasks[target:getName()]
  if taskId then
    local task = Task_Config.Tasks[taskId]
    if task then
      local party = player:getParty()
      if party and Task_Config.Party.Enabled then
        local members = party:getMembers()
        table.insert(members, party:getLeader())

        local killerPos = player:getPosition()
        for _, member in ipairs(members) do
          if Task_Config.Party.Range > 0 then
            if member:getPosition():getDistance(killerPos) <= Config.Party.Range then
              member:taskProcessKill(taskId)
            end
          else
            member:taskProcessKill(taskId)
          end
        end
      else
        player:taskProcessKill(taskId)
      end
    end
  end

  return true
end

function Player:taskProcessKill(taskId)
  local slot = self:getSlotByTaskId(taskId)
  if slot then
    self:addTaskKill(slot)

    local requiredKills = self:getTaskRequiredKills(slot)
    local kills = self:getTaskKills(slot)
    if kills >= requiredKills then
      self:setStorageValue(Task_Config.StorageSlot + slot, -1)
      self:setStorageValue(Task_Config.StorageKillsCurrent + slot, -1)
      self:setStorageValue(Task_Config.StorageKillsSelected + slot, -1)

      local task = Task_Config.Tasks[taskId]
      for _, reward in ipairs(task.Rewards) do
        self:addTaskReward(reward, requiredKills)
      end
      self:sendTextMessage(MESSAGE_STATUS_CONSOLE_ORANGE, "[Task Status] You have finished " .. task.RaceName .. " task!")
    end
    self:sendTaskUpdate(taskId)
  end
end

function Player:addTaskReward(reward, requiredKills)
  local bonus = math.floor((math.max(0, requiredKills - Task_Config.KillsForBonus) / Task_Config.KillsForBonus) + 0.5)
  if reward.Type == RewardType.Points then
    bonus = bonus * Task_Config.PointsIncrease
    local value = reward.BaseValue + math.floor((reward.BaseValue * bonus / 100) + 0.5)
    self:addTasksPoints(value)
    self:sendTextMessage(
      MESSAGE_STATUS_CONSOLE_ORANGE,
      "[Task Reward] Tasks Points +" .. value .. ", you have now " .. self:getTasksPoints() .. " tasks points."
    )
  elseif reward.Type == RewardType.Experience then
    bonus = bonus * Task_Config.ExperienceIncrease
    local value = reward.BaseValue + math.floor((reward.BaseValue * bonus / 100) + 0.5)
    self:addExperience(value, true)
    self:sendTextMessage(MESSAGE_STATUS_CONSOLE_ORANGE, "[Task Reward] Experience +" .. value .. ".")
  elseif reward.Type == RewardType.Gold then
    bonus = bonus * Task_Config.GoldIncrease
    local value = reward.BaseValue + math.floor((reward.BaseValue * bonus / 100) + 0.5)
    self:setBankBalance(self:getBankBalance() + value)
    self:sendTextMessage(MESSAGE_STATUS_CONSOLE_ORANGE, "[Task Reward] " .. value .. " gold added to your bank.")
  elseif reward.Type == RewardType.Item then
    local itemType = ItemType(reward.Id)
    local itemWeight = itemType:getWeight(reward.Amount)
    local playerCap = self:getFreeCapacity()
    if playerCap >= itemWeight then
      self:addItem(reward.Id, reward.Amount)
      self:sendTextMessage(MESSAGE_STATUS_CONSOLE_ORANGE, "[Task Reward] " .. reward.Amount .. "x " .. itemType:getName() .. ".")
    else
      self:getStoreInbox():addItem(reward.Id, reward.Amount)
      self:sendTextMessage(
        MESSAGE_STATUS_CONSOLE_ORANGE,
        "[Task Reward] Low on capacity, sending " .. reward.Amount .. "x " .. itemType:getName() .. " to your Purse."
      )
    end
  elseif reward.Type == RewardType.Storage then
    if self:getStorageValue(reward.Key) ~= reward.Value then
      self:setStorageValue(reward.Key, reward.Value)
      self:sendTextMessage(MESSAGE_STATUS_CONSOLE_ORANGE, '[Task Reward] You have been granted "' .. reward.Description .. '".')
    end
  elseif reward.Type == RewardType.Teleport then
    self:teleportTo(reward.Position)
    self:sendTextMessage(MESSAGE_STATUS_CONSOLE_ORANGE, '[Task Reward] You have been teleported to "' .. reward.Description .. '".')
  end
end

function Player:getTaskIdBySlot(slot)
  return math.max(0, self:getStorageValue(Task_Config.StorageSlot + slot))
end

function Player:getSlotByTaskId(taskId)
  for i = 1, Task_Config.ActiveTasksLimit do
    local slotTask = self:getTaskIdBySlot(i)
    if taskId == slotTask then
      return i
    end
  end

  return nil
end

function Player:getTaskKills(slot)
  return math.max(0, self:getStorageValue(Task_Config.StorageKillsCurrent + slot))
end

function Player:getTaskRequiredKills(slot)
  return math.max(0, self:getStorageValue(Task_Config.StorageKillsSelected + slot))
end

function Player:addTaskKill(slot)
  self:setStorageValue(Task_Config.StorageKillsCurrent + slot, self:getTaskKills(slot) + 1)
end

function Player:addTasksPoints(points)
  self:setStorageValue(Task_Config.StoragePoints, self:getTasksPoints() + points)
  self:sendTasksPointsUpdate()
end

function Player:getTasksPoints()
  return math.max(0, self:getStorageValue(Task_Config.StoragePoints))
end

function Player:getTasksRank()
  local rank = self:getTasksPoints()
  if rank >= Cache.LastRank then
    return Cache.Ranks[Cache.LastRank]
  end

  return Cache.Ranks[rank]
end

function Player:getFreeTaskSlot()
  for i = 1, Task_Config.ActiveTasksLimit do
    if self:getTaskIdBySlot(i) == 0 then
      return i
    end
  end

  return nil
end

function MonsterType:getOutfitOTC()
  local outfit = self:outfit()
  return {
    type = outfit.lookType,
    auxType = outfit.lookTypeEx,
    head = outfit.lookHead,
    body = outfit.lookBody,
    legs = outfit.lookLegs,
    feet = outfit.lookFeet,
    addons = outfit.lookAddons,
    mount = outfit.lookMount
  }
end
 

Similar threads

Back
Top