Guest User

Neobot Files Backup Highlighted

a guest
Jun 19th, 2012
306
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lua 424.55 KB | None | 0 0
  1.  
  2. NEOBOT HELP FILES BACKUP 30/09/11
  3.  
  4.  
  5. --------------------------------------------
  6. -------------LIBRARIES FILES CONTENTS-------
  7. --------------------------------------------
  8.  
  9.  
  10. ------------------------------sirmate.lua---------------------------------
  11.  
  12.  
  13. SIRMATE_LIB = '1.3'
  14. print('sirmate library loaded. version: ' .. SIRMATE_LIB .. '.')
  15.  
  16. -- [[ Vocation names ]] --
  17. VOCATIONS = {'druid', 'elder druid', 'elite knight', 'knight', 'master sorcerer', 'paladin', 'royal paladin', 'sorcerer'}
  18. BASIC_VOCATIONS = {'druid', 'knight', 'paladin', 'sorcerer'}
  19. PROMOTED_VOCATIONS = {'elder druid', 'elite knight', 'master sorcerer', 'royal paladin'}
  20.  
  21. -- [[ Outfits IDs ]] --
  22. FREE_OUTFITS = {128, 129, 130, 131, 136, 137, 138, 139}
  23. PREMIUM_OUTFITS = {132, 133, 134, 140, 141, 142, 143, 144, 145, 146, 147, 148, 149, 150, 151, 152, 153, 154, 155, 156, 157, 158, 251, 252, 268, 269, 270, 273, 278, 279, 288, 289, 324, 325, 328, 329, 335, 336, 366, 367}
  24. MALE_OUTFITS = {128, 129, 130, 131, 132, 133, 134, 143, 144, 145, 146, 151, 152, 153, 154, 251, 268, 273, 278, 289, 325, 328, 335, 367}
  25. FEMALE_OUTFITS = {136, 137, 138, 139, 140, 141, 142, 147, 148, 149, 150, 155, 156, 157, 158, 252, 269, 270, 279, 288, 324, 329, 336, 366}
  26.  
  27. -- [[ Param and Haste spells ]] --
  28. PARAM_SPELLS = {'utevo res ina', 'exiva', 'exura sio', 'exani hur', 'utevo res'}
  29. HASTE_SPELLS = {'utani hur', 'utani gran hur', 'utani tempo hur', 'utamo tempo san'}
  30.  
  31. -- [[ List of supplies items ]] --
  32. POTIONS_AND_RUNES = {'antidote potion', 'berserk potion', 'bullseye potion', 'great health potion', 'great mana potion', 'great spirit potion', 'health potion', 'mana potion', 'mastermind potion', 'small health potion', 'strong health potion', 'strong mana potion', 'ultimate health potion', 'animate dead rune', 'avalanche rune', 'chameleon rune', 'convince creature rune', 'cure poison rune', 'desintegrate rune', 'destroy field rune', 'energy bomb rune', 'energy field rune', 'energy wall rune', 'explosion rune', 'fire bomb rune', 'fire field rune', 'fire wall rune', 'fireball rune', 'great fireball rune', 'heavy magic missile rune', 'holy missile rune', 'icicle rune', 'intense healing rune', 'light magic missile rune', 'magic wall rune', 'paralyze rune', 'poison bomb rune', 'poison field rune', 'poison wall rune', 'soulfire rune', 'stalagmite rune', 'stone shower rune', 'sudden death rune', 'thunderstorm rune', 'ultimate healing rune', 'wild growth rune'}
  33. AMMUNITION = {'arrow', 'burst arrow', 'earth arrow', 'flaming arrow', 'flash arrow', 'onyx arrow', 'poison arrow', 'shiver arrow', 'sniper arrow', 'bolt', 'infernal bolt', 'piercing bolt', 'power bolt'}
  34. DISTANCE_WEAPONS = {'assassin star', 'enchanted spear', 'hunting spear', 'royal spear', 'small stone', 'snowball', 'spear', 'throwing Knife', 'throwing star', 'viper star'}
  35.  
  36. -- [[ Stats clear constants ]] --
  37. SC_ALL_SECTIONS = 0
  38. SC_MONSTERS_SEEN = 1
  39. SC_PLAYERS_SEEN = 2
  40. SC_MONSTERS_KILLED = 3
  41. SC_ITEMS_LOOTED = 4
  42. SC_SUPPLIES_USED = 5
  43. SC_DAMAGE_DEALT = 6
  44. SC_DAMAGE_RECEIVED = 7
  45. SC_DAMAGE_STATS = 8
  46. SC_HEAL_STATS = 9
  47.  
  48. local BINARY_INSERT_COMPARE_FUNCTION_NOKEY = function(first, second) return first < second end
  49. local BINARY_INSERT_COMPARE_FUNCTION_WITHKEY = function(first, second, argument) return first[argument] < second[argument] end
  50.  
  51. function table.binaryinsert(self, value, argument) -- Working
  52.     local compare_function
  53.     if (type(argument) == 'function') then
  54.         compare_function = argument
  55.     elseif (type(argument) == 'string') then
  56.         compare_function = BINARY_INSERT_COMPARE_FUNCTION_WITHKEY
  57.     else
  58.         compare_function = BINARY_INSERT_COMPARE_FUNCTION_NOKEY
  59.     end
  60.  
  61.     local left, right, mid, state = 1, #self, 1, 0
  62.     while (left <= right) do
  63.         mid = math.floor((left + right) / 2)
  64.  
  65.         if (compare_function(value, self[mid], ((type(argument) == 'string' and argument) or nil))) then
  66.             right, state = mid - 1, 0
  67.         else
  68.             left, state = mid + 1, 1
  69.         end
  70.     end
  71.  
  72.     table.insert(self, mid + state, value)
  73.     return mid + state
  74. end
  75.  
  76. function arguments(function_name, function_arguments) -- Working
  77.     for i = 1, #function_arguments, 2 do
  78.         if (type(function_arguments[i + 1]) ~= function_arguments[i]) then
  79.             return false, error('bad argument #' .. math.ceil(i / 2)  .. ' to \'' .. function_name .. '\' (' .. function_arguments[i] .. ' expected, got ' .. type(function_arguments[i + 1]) .. ')', 3)
  80.         end
  81.     end
  82. end
  83.  
  84. local UNIT_DATA_FILE = 'player.data'
  85. local UNIT_DATA_RUN_LAST = $timems
  86. local UNIT_DATA_RUN_DELAY = 100
  87. local UNIT_DATA_SAVE_LAST = $timems
  88. local UNIT_DATA_SAVE_DELAY = 60000
  89.  
  90. Unit = {
  91.     data = {}
  92. }
  93.  
  94. function Unit:getPlayersData(cache_players_data) -- Working
  95.     if (type(cache_players_data) ~= 'boolean') then cache_players_data = false end
  96.  
  97.     if (UNIT_DATA_RUN_LAST + UNIT_DATA_RUN_DELAY >= $timems) then return end
  98.    
  99.     if (#self.data == 0 and cache_players_data) then
  100.         if (#filecontent(UNIT_DATA_FILE) ~= 0) then
  101.             self.data = dofile('neofiles/' .. UNIT_DATA_FILE .. '.txt')
  102.             table.newsort(self.data, 'name', 'asc')
  103.         end
  104.     end
  105.  
  106.     foreach newmessage m do
  107.         if (table.find({MSG_CHANNEL, MSG_DEFAULT, MSG_PVT, MSG_SENT, MSG_TUTOR, MSG_WHISPER, MSG_YELL}, m.type) and m.level ~= 0) then
  108.             local message_sender = m.sender:lower()
  109.             local player_found = table.binaryfind(self.data, message_sender, 'name')
  110.  
  111.             if (player_found) then
  112.                 self.data[player_found].level = tonumber(m.level)
  113.             else
  114.                 table.binaryinsert(self.data, {name = message_sender, level = tonumber(m.level), sex = 'unknown', vocation = 'unknown', gname = '', grank = '', gtitle = '', spells = {}}, 'name')
  115.                 player_found = table.binaryfind(self.data, message_sender, 'name')
  116.             end
  117.  
  118.             if (m.type == MSG_DEFAULT) then
  119.                 local message_content = m.content
  120.  
  121.                 for _, param_spell in ipairs(PARAM_SPELLS) do
  122.                     if (message_content:match("^" .. param_spell .. " \".+")) then
  123.                         message_content = param_spell break
  124.                     end
  125.                 end
  126.  
  127.                 local spell_info = Spell:getInfo(message_content, 'words')
  128.  
  129.                 if (type(spell_info) == 'table' and tonumber(m.level) >= spell_info.level) then
  130.                     local spell_found = table.binaryfind(self.data[player_found].spells, spell_info.name, 'name')
  131.  
  132.                     if (table.find(HASTE_SPELLS, spell_info.words)) then
  133.                         for _, haste_spell in ipairs(HASTE_SPELLS) do
  134.                             local haste_spell_info = Spell:getInfo(haste_spell)
  135.                             local haste_spell_found = table.find(self.data[player_found].spells, haste_spell_info.name, 'name')
  136.  
  137.                             if (haste_spell_found) then
  138.                                 self.data[player_found].spells[haste_spell_found].lastuse = $timems - 1000 - ((haste_spell_info.cooldown > haste_spell_info.duration and haste_spell_info.cooldown) or haste_spell_info.duration) * 1000
  139.                             end
  140.                         end
  141.                     end
  142.                    
  143.                     if (spell_found) then
  144.                         self.data[player_found].spells[spell_found].lastuse = $timems
  145.                     else
  146.                         table.binaryinsert(self.data[player_found].spells, {name = spell_info.name, lastuse = $timems}, 'name')
  147.                     end
  148.                    
  149.                     if (not table.binaryfind(PROMOTED_VOCATIONS, self.data[player_found].vocation) and #self.data[player_found].spells ~= 0) then Unit:getVocation(message_sender) end
  150.                 end
  151.             end
  152.         elseif (m.type == MSG_INFO and m.content:match('^You see')) then
  153.             local player_name, player_level, player_sex, player_vocation, player_guildinfo = string.match(m.content, "You see (.+) %(.-(%d+).- ([S]?[hH]e) is an? (.-)%.(.*)")
  154.             local player_guild_name, player_guild_rank, player_guild_title = '', '', ''
  155.  
  156.             if (#(player_guildinfo or '') > 0) then
  157.                 player_guild_rank, player_guild_name = string.match(player_guildinfo, ".-is (.+) of the (.+)%.")
  158.  
  159.                 if (string.find(player_guild_name, "%(")) then
  160.                     player_guild_name, player_guild_title = string.match(player_guild_name, "(.+) %((.+)%)")
  161.                 end
  162.             end
  163.  
  164.             if (player_name and player_level and player_sex and player_vocation and player_guild_name and player_guild_rank and player_guild_title) then
  165.                 player_name = player_name:lower()
  166.                 local player_found = table.binaryfind(self.data, player_name, 'name')
  167.  
  168.                 if (player_found) then
  169.                     self.data[player_found] = {name = player_name, level = tonumber(player_level), sex = (player_sex == 'He' and 'male') or 'female', vocation = player_vocation, gname = player_guild_name:lower(), grank = player_guild_rank:lower(), gtitle = player_guild_title:lower(), spells = self.data[player_found].spells}
  170.                 else
  171.                     table.binaryinsert(self.data, {name = player_name, level = tonumber(player_level), sex = (player_sex == 'He' and 'male') or 'female', vocation = player_vocation, gname = player_guild_name:lower(), grank = player_guild_rank:lower(), gtitle = player_guild_title:lower(), spells = {}}, 'name')
  172.                 end
  173.             end
  174.         end
  175.     end
  176.  
  177.     if (UNIT_DATA_SAVE_LAST + UNIT_DATA_SAVE_DELAY <= $timems and cache_players_data) then
  178.         local PLAYER_DATA = ''
  179.         for _, p in ipairs(self.data) do
  180.             PLAYER_DATA = PLAYER_DATA .. '  {name = "'.. p.name .. '", level = '.. p.level .. ', sex = "'.. p.sex .. '", vocation = "'.. p.vocation .. '", gname = "'.. p.gname .. '", grank = "'.. p.grank .. '", gtitle = "'.. p.gtitle .. '", spells = {}},\n'
  181.         end
  182.  
  183.         filerewrite(UNIT_DATA_FILE, 'return {\n' .. PLAYER_DATA .. '}')
  184.         UNIT_DATA_SAVE_LAST = $timems
  185.     end
  186.    
  187.     UNIT_DATA_RUN_LAST = $timems
  188. end
  189.  
  190. function Unit:getName(unit_name) -- Working
  191.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  192.         if (type(unit_name) == 'number') then
  193.             unit_name = findcreature(unit_name)
  194.         end
  195.  
  196.         if (self:isPlayer(unit_name) or self:isMonster(unit_name) or self:isNPC(unit_name)) then
  197.             return ((unit_name.name ~= nil and unit_name.name) or unit_name):lower()
  198.         end
  199.     end
  200.  
  201.     return nil
  202. end
  203.  
  204. function Unit:getLevel(unit_name) -- Working
  205.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  206.         if (type(unit_name) == 'number') then
  207.             unit_name = findcreature(unit_name)
  208.         end
  209.  
  210.         if (((unit_name.name ~= nil and unit_name.name) or unit_name):lower() == $name:lower()) then
  211.             return $level
  212.         elseif (self:isPlayer(unit_name)) then
  213.             if (type(unit_name) == 'userdata') then unit_name = unit_name.name end
  214.             local unit_found = table.binaryfind(self.data, unit_name:lower(), 'name')
  215.  
  216.             if (unit_found) then
  217.                 return self.data[unit_found].level
  218.             end
  219.         end
  220.     end
  221.  
  222.     return 0
  223. end
  224.  
  225. function Unit:getSex(unit_name) -- Working
  226.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  227.         if (type(unit_name) == 'number') then
  228.             unit_name = findcreature(unit_name)
  229.         end
  230.  
  231.         if self:isPlayer(unit_name) then
  232.             local unit_found = table.binaryfind(self.data, ((unit_name.name ~= nil and unit_name.name) or unit_name):lower(), 'name')
  233.  
  234.             if (unit_found) then
  235.                 if (type(unit_name) == 'userdata' and self.data[unit_found].sex == 'unknown') then
  236.                     if (table.binaryfind(MALE_OUTFITS, unit_name.outfit)) then
  237.                         self.data[unit_found].sex = 'male'
  238.                     elseif (table.binaryfind(FEMALE_OUTFITS, unit_name.outfit)) then
  239.                         self.data[unit_found].sex = 'female'
  240.                     end
  241.                 end
  242.  
  243.                 return self.data[unit_found].sex
  244.             end
  245.         end
  246.     end
  247.  
  248.     return 'unknown'
  249. end
  250.  
  251. function Unit:getVocation(unit_name, basic) -- Working
  252.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  253.         if (type(unit_name) == 'number') then unit_name = findcreature(unit_name) end
  254.         if (type(basic) ~= 'boolean') then basic = false end
  255.  
  256.         if (self:isPlayer(unit_name)) then
  257.             if (type(unit_name) == 'userdata') then unit_name = unit_name.name end
  258.             local unit_found, player_vocation = table.binaryfind(self.data, unit_name:lower(), 'name'), 'unknown'
  259.  
  260.             if (unit_found) then
  261.                 player_vocation = self.data[unit_found].vocation
  262.  
  263.                 if (table.binaryfind(PROMOTED_VOCATIONS, self.data[unit_found].vocation)) then
  264.                     player_vocation = self.data[unit_found].vocation
  265.                 elseif (not table.binaryfind(PROMOTED_VOCATIONS, self.data[unit_found].vocation) and #self.data[unit_found].spells ~= 0) then
  266.                     for _, spell in ipairs(self.data[unit_found].spells) do
  267.                         local spell_info = Spell:getInfo(spell.name, 'name')
  268.  
  269.                         if (type(spell_info) == 'table') then
  270.                             if (spell_info.vocation ~= false) then
  271.                                 player_vocation, self.data[unit_found].vocation = spell_info.vocation, spell_info.vocation
  272.                                 if (table.binaryfind(PROMOTED_VOCATIONS, spell_info.vocation)) then break end
  273.                             end
  274.                         end
  275.                     end
  276.                 end
  277.  
  278.                 if (unit_name:lower() == $name:lower() and player_vocation == 'unknown') then
  279.                     local _vocation = vocation()
  280.  
  281.                     if (_vocation ~= 'mage') then
  282.                         player_vocation, self.data[unit_found].vocation = _vocation, _vocation
  283.                     end
  284.                 end
  285.             end
  286.  
  287.             if (basic) then
  288.                 return player_vocation:gsub('master ', ''):gsub('elite ', ''):gsub('elder ', ''):gsub('royal ', '')
  289.             end
  290.  
  291.             return player_vocation
  292.         end
  293.     end
  294.  
  295.     return 'unknown'
  296. end
  297.  
  298. function Unit:getGuildInfo(unit_name) -- Working
  299.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  300.         if (type(unit_name) == 'number') then unit_name = findcreature(unit_name) end
  301.  
  302.         if (self:isPlayer(unit_name)) then
  303.             local unit_found = table.binaryfind(self.data, ((unit_name.name ~= nil and unit_name.name) or unit_name):lower(), 'name')
  304.  
  305.             if (unit_found) then
  306.                 if (#self.data[unit_found].gname ~= 0) then
  307.                     return {name = self.data[unit_found].gname, rank = self.data[unit_found].grank, title = self.data[unit_found].gtitle}
  308.                 end
  309.             end
  310.         end
  311.     end
  312.  
  313.     return {name = '', rank = '', title = ''}
  314. end
  315.  
  316. function Unit:getHealth(unit_name) -- Working
  317.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  318.         if (type(unit_name) == 'number') then
  319.             unit_name = findcreature(unit_name)
  320.         end
  321.  
  322.         if (((unit_name.name ~= nil and unit_name.name) or unit_name):lower() == $name:lower()) then
  323.             return $hp
  324.         else
  325.             local unit_health_percent, unit_health_max = self:getHealthPercent(unit_name), self:getHealthMax(unit_name)
  326.  
  327.             if (unit_health_percent ~= 0 and unit_health_max ~= 0) then
  328.                 return math.floor((unit_health_percent / 100) * unit_health_max)
  329.             end
  330.         end
  331.     end
  332.  
  333.     return 0
  334. end
  335.  
  336. function Unit:getHealthPercent(unit_name) -- Working
  337.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  338.         if (type(unit_name) ~= 'userdata') then
  339.             unit_name = findcreature(unit_name)
  340.         end
  341.  
  342.         if (type(unit_name) == 'userdata') then
  343.             return unit_name.hppc
  344.         end
  345.     end
  346.  
  347.     return 0
  348. end
  349.  
  350. function Unit:getHealthMax(unit_name) -- Working
  351.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  352.         if (type(unit_name) == 'number') then
  353.             unit_name = findcreature(unit_name)
  354.         end
  355.  
  356.         if (((unit_name.name ~= nil and unit_name.name) or unit_name):lower() == $name:lower()) then
  357.             return $maxhp
  358.         end
  359.  
  360.         if (type(unit_name) == 'userdata') then
  361.             unit_name = unit_name.name
  362.         end
  363.  
  364.         if (self:isMonster(unit_name)) then
  365.             return creatureinfo(unit_name).hp
  366.         else
  367.             local unit_found = table.binaryfind(self.data, unit_name:lower(), 'name')
  368.  
  369.             if (unit_found) then
  370.                 if (table.binaryfind({'elite knight', 'knight'}, self.data[unit_found].vocation)) then
  371.                     return (self.data[unit_found].level * 15) + 65
  372.                 elseif (table.binaryfind({'paladin', 'royal paladin'}, self.data[unit_found].vocation)) then
  373.                     return (self.data[unit_found].level * 10) + 105
  374.                 else
  375.                     return (self.data[unit_found].level * 5) + 145
  376.                 end
  377.             end
  378.         end
  379.     end
  380.  
  381.     return 0
  382. end
  383.  
  384. function Unit:getMana(unit_name) -- Working
  385.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  386.         if (type(unit_name) == 'number') then
  387.             unit_name = findcreature(unit_name)
  388.         end
  389.  
  390.         if (((unit_name.name ~= nil and unit_name.name) or unit_name):lower() == $name:lower()) then
  391.             return $mp
  392.         end
  393.     end
  394.  
  395.     return 0
  396. end
  397.  
  398. function Unit:getManaPercent(unit_name) -- Working
  399.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  400.         if (type(unit_name) == 'number') then
  401.             unit_name = findcreature(unit_name)
  402.         end
  403.  
  404.         if (((unit_name.name ~= nil and unit_name.name) or unit_name):lower() == $name:lower()) then
  405.             return $mppc
  406.         end
  407.     end
  408.  
  409.     return 0
  410. end
  411.  
  412. function Unit:getManaMax(unit_name) -- Working
  413.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  414.         if (type(unit_name) == 'number') then
  415.             unit_name = findcreature(unit_name)
  416.         end
  417.  
  418.         if (((unit_name.name ~= nil and unit_name.name) or unit_name):lower() == $name:lower()) then
  419.             return $maxmp
  420.         elseif (self:isPlayer(unit_name)) then
  421.             local unit_found = table.binaryfind(self.data, ((unit_name.name ~= nil and unit_name.name) or unit_name):lower(), 'name')
  422.  
  423.             if (unit_found) then
  424.                 if (table.binaryfind({'druid', 'elder druid', 'master sorcerer', 'sorcerer'}, self.data[unit_found].vocation)) then
  425.                     return (self.data[unit_found].level * 30) - 205
  426.                 elseif (table.binaryfind({'paladin', 'royal paladin'}, self.data[unit_found].vocation)) then
  427.                     return (self.data[unit_found].level * 15) - 85
  428.                 else
  429.                     return (self.data[unit_found].level * 5) - 5
  430.                 end
  431.             end
  432.         end
  433.     end
  434.  
  435.     return 0
  436. end
  437.  
  438. function Unit:getBaseSpeed(unit_name) -- Working
  439.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  440.         if (type(unit_name) == 'number') then
  441.             unit_name = findcreature(unit_name)
  442.         end
  443.  
  444.         if (self:getLevel(unit_name) ~= 0) then
  445.             return 220 + (2 * (self:getLevel(unit_name) - 1))
  446.         end
  447.     end
  448.  
  449.     return 0
  450. end
  451.  
  452. function Unit:getCastedSpells(unit_name) -- Working
  453.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  454.         if (type(unit_name) == 'number') then
  455.             unit_name = findcreature(unit_name)
  456.         end
  457.  
  458.         if (self:isPlayer(unit_name)) then
  459.             local unit_found = table.binaryfind(self.data, ((unit_name.name ~= nil and unit_name.name) or unit_name):lower(), 'name')
  460.  
  461.             if (unit_found) then
  462.                 return self.data[unit_found].spells
  463.             end
  464.         end
  465.     end
  466.  
  467.     return {}
  468. end
  469.  
  470. function Unit:getActiveSpells(unit_name) -- Working
  471.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  472.         if (type(unit_name) == 'number') then
  473.             unit_name = findcreature(unit_name)
  474.         end
  475.  
  476.         local active_spells = {}
  477.        
  478.         for _, spell in ipairs(self:getCastedSpells(unit_name)) do
  479.             local spell_info = Spell:getInfo(spell.name, 'name')
  480.             local spell_time = ((spell_info.cooldown > spell_info.duration and spell_info.cooldown) or spell_info.duration) * 1000
  481.  
  482.             if (spell.lastuse + spell_time >= $timems) then
  483.                 table.binaryinsert(active_spells, {name = spell_info.name, time = spell.lastuse - $timems + spell_time, group = spell_info.group1}, 'name')
  484.             end
  485.         end
  486.        
  487.         return active_spells
  488.     end
  489.  
  490.     return {}
  491. end
  492.  
  493. function Unit:getCooldown(unit_name, spell_name, group_cooldown) -- Working
  494.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  495.         if (type(unit_name) == 'number') then
  496.             unit_name = findcreature(unit_name)
  497.         end
  498.  
  499.         if (self:isPlayer(unit_name)) then
  500.             if (type(unit_name) == 'userdata') then unit_name = unit_name.name end
  501.             local unit_found = table.binaryfind(self.data, unit_name:lower(), 'name')
  502.  
  503.             if (unit_found and type(spell_name) ~= 'nil') then
  504.                 spell_name = spell_name:lower()
  505.                 if (type(group_cooldown) ~= 'nil') then group_cooldown = true end
  506.                 local function getGroupCooldown(unit_name, group_name)
  507.                     local group_times = {attack = 2000, healing = 1000, special = 8000, support = 2000}
  508.  
  509.                     if (unit_name:lower() == $name:lower()) then
  510.                         return cooldown(group_name), group_times[group_name]
  511.                     end
  512.  
  513.                     for _, spell in ipairs(Spell.data) do
  514.                         if spell.group1 == group_name then
  515.                             local spell_found = table.binaryfind(self.data[unit_found].spells, spell.name, 'name')
  516.  
  517.                             if (type(spell_found) ~= 'nil') then
  518.                                 local spell_lastuse = self.data[unit_found].spells[spell_found].lastuse
  519.  
  520.                                 if (spell_lastuse + group_times[group_name] >= $timems) then
  521.                                     return spell_lastuse - $timems + group_times[group_name], group_times[group_name]
  522.                                 end
  523.                             end
  524.                         end
  525.                     end
  526.  
  527.                     return 0, group_times[group_name]
  528.                 end
  529.  
  530.                 if table.binaryfind({'attack', 'healing', 'special', 'support'}, spell_name) then
  531.                     return getGroupCooldown(unit_name, spell_name)
  532.                 else
  533.                     local spell_info = Spell:getInfo(spell_name)
  534.  
  535.                     if (type(spell_info) ~= 'nil') then
  536.                         local spell_found = table.binaryfind(self.data[unit_found].spells, spell_info.name, 'name')
  537.                         local spell_time = ((spell_info.cooldown > spell_info.duration and spell_info.cooldown) or spell_info.duration) * 1000
  538.  
  539.                         if (type(spell_found) ~= 'nil') then
  540.                             local spell_lastuse = self.data[unit_found].spells[spell_found].lastuse
  541.  
  542.                             if (spell_lastuse + spell_time >= $timems) then
  543.                                 return spell_lastuse - $timems + spell_time, spell_time
  544.                             end
  545.                         end
  546.  
  547.                         if (group_cooldown) then
  548.                             return getGroupCooldown(unit_name, spell_info.group1)
  549.                         end
  550.                     end
  551.                 end
  552.             end
  553.         end
  554.     end
  555.  
  556.     return 0, 0
  557. end
  558.  
  559. function Unit:isPlayer(unit_name) -- Working
  560.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  561.         if (type(unit_name) == 'number') then
  562.             unit_name = findcreature(unit_name)
  563.         end
  564.  
  565.         if (table.binaryfind(self.data, ((unit_name.name ~= nil and unit_name.name) or unit_name):lower(), 'name')) then
  566.             return true
  567.         end
  568.  
  569.         if (type(unit_name) ~= 'userdata') then
  570.             unit_name = findcreature(unit_name)
  571.         end
  572.  
  573.         if (type(unit_name) == 'userdata') then
  574.             return unit_name.isplayer
  575.         end
  576.     end
  577.  
  578.     return false
  579. end
  580.  
  581. function Unit:isMonster(unit_name) -- Working
  582.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  583.         if (type(unit_name) ~= 'userdata') then
  584.             unit_name = findcreature(unit_name)
  585.         end
  586.  
  587.         if (type(unit_name) == 'userdata') then
  588.             return unit_name.ismonster and type(creatureinfo(unit_name.name)) == 'table'
  589.         end
  590.     end
  591.  
  592.     return false
  593. end
  594.  
  595. function Unit:isNPC(unit_name) -- Working
  596.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  597.         if (type(unit_name) ~= 'userdata') then
  598.             unit_name = findcreature(unit_name)
  599.         end
  600.  
  601.         if (type(unit_name) == 'userdata') then
  602.             return unit_name.ismonster and type(creatureinfo(unit_name.name)) ~= 'table'
  603.         end
  604.     end
  605.  
  606.     return false
  607. end
  608.  
  609. function Unit:isPremium(unit_name) -- Working
  610.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  611.         if (type(unit_name) ~= 'userdata') then
  612.             unit_name = findcreature(unit_name)
  613.         end
  614.  
  615.         if (type(unit_name) == 'userdata') then
  616.             if (self:isPlayer(unit_name)) then
  617.                 if (self:isPromoted(unit_name)) then
  618.                     return true
  619.                 end
  620.  
  621.                 if (self:isMounted(unit_name)) then
  622.                     return true
  623.                 end
  624.  
  625.                 if ((table.find(FREE_OUTFITS, unit_name.outfit) and unit_name.addons ~= 0) or table.find(PREMIUM_OUTFITS, unit_name.outfit)) then
  626.                     return true
  627.                 end
  628.             end
  629.         end
  630.     end
  631.  
  632.     return false
  633. end
  634.  
  635. function Unit:isPromoted(unit_name) -- Working
  636.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  637.         if (type(unit_name) ~= 'userdata') then
  638.             unit_name = findcreature(unit_name)
  639.         end
  640.  
  641.         if (self:isPlayer(unit_name)) then
  642.             if (table.binaryfind(PROMOTED_VOCATIONS, self:getVocation(unit_name))) then
  643.                 return true
  644.             end
  645.         end
  646.     end
  647.  
  648.     return false
  649. end
  650.  
  651. function Unit:isMounted(unit_name) -- Working
  652.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  653.         if (type(unit_name) ~= 'userdata') then
  654.             unit_name = findcreature(unit_name)
  655.         end
  656.  
  657.         if (type(unit_name) == 'userdata') then
  658.             return unit_name.mount ~= 0
  659.         end
  660.     end
  661.  
  662.     return false
  663. end
  664.  
  665. function Unit:isParalyzed(unit_name) -- Working
  666.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  667.         if (type(unit_name) ~= 'userdata') then
  668.             unit_name = findcreature(unit_name)
  669.         end
  670.  
  671.         if (type(unit_name) == 'userdata') then
  672.             return unit_name.speed < self:getBaseSpeed(unit_name)
  673.         end
  674.     end
  675.  
  676.     return false
  677. end
  678.  
  679. function Unit:isStealthed(unit_name) -- Working
  680.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  681.         if (type(unit_name) ~= 'userdata') then
  682.             unit_name = findcreature(unit_name)
  683.         end
  684.  
  685.         if (type(unit_name) == 'userdata') then
  686.             return unit_name.outfit == 0
  687.         end
  688.     end
  689.  
  690.     return false
  691. end
  692.  
  693. function Unit:isSwimming(unit_name) -- Working
  694.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  695.         if (type(unit_name) ~= 'userdata') then
  696.             unit_name = findcreature(unit_name)
  697.         end
  698.  
  699.         if (type(unit_name) == 'userdata') then
  700.             return unit_name.outfit == 267
  701.         end
  702.     end
  703.  
  704.     return false
  705. end
  706.  
  707. function Unit:isInMyGuild(unit_name) -- Working
  708.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  709.         if (type(unit_name) == 'number') then
  710.             unit_name = findcreature(unit_name)
  711.         end
  712.  
  713.         if (self:isPlayer(unit_name)) then
  714.             local self_guild = self:getGuildInfo($name)
  715.             local unit_guild = self:getGuildInfo((unit_name.name ~= nil and unit_name.name) or unit_name)
  716.  
  717.             if (self_guild and unit_guild) then
  718.                 if (#self_guild.name ~= 0 and #unit_guild.name ~= 0) then
  719.                     return self_guild.name == unit_guild.name
  720.                 end
  721.             end
  722.         end
  723.     end
  724.  
  725.     return false
  726. end
  727.  
  728. function Unit:isInParty(unit_name) -- Working
  729.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  730.         if (type(unit_name) ~= 'userdata') then
  731.             unit_name = findcreature(unit_name)
  732.         end
  733.  
  734.         if (type(unit_name) == 'userdata') then
  735.             return unit_name.party ~= PARTY_NOPARTY and unit_name.party ~= PARTY_INVITED_LEADER and unit_name.party ~= PARTY_INVITED_MEMBER
  736.         end
  737.     end
  738.  
  739.     return false
  740. end
  741.  
  742. function Unit:isPartyLeader(unit_name) -- Working
  743.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  744.         if (type(unit_name) ~= 'userdata') then
  745.             unit_name = findcreature(unit_name)
  746.         end
  747.  
  748.         if (type(unit_name) == 'userdata') then
  749.             return unit_name.party == PARTY_EXPSHARE_OK_LEADER or unit_name.party == PARTY_EXPSHARE_OFF_LEADER or unit_name.party == PARTY_EXPSHARE_WAIT_LEADER or unit_name.party == PARTY_ONPARTY_LEADER
  750.         end
  751.     end
  752.  
  753.     return false
  754. end
  755.  
  756. function Unit:canMount(unit_name) -- Working
  757.     if (table.find({'number', 'string', 'userdata'}, type(unit_name))) then
  758.         if (type(unit_name) ~= 'userdata') then
  759.             unit_name = findcreature(unit_name)
  760.         end
  761.  
  762.         if (type(unit_name) == 'userdata') then
  763.             if (self:isPlayer(unit_name)) then
  764.                 if (not self:isMounted(unit_name) and (table.binaryfind(FREE_OUTFITS, unit_name.outfit) or table.binaryfind(PREMIUM_OUTFITS, unit_name.outfit))) then
  765.                     return true
  766.                 end
  767.             end
  768.         end
  769.     end
  770.  
  771.     return false
  772. end
  773.  
  774. Spell = {
  775.     data = {
  776.         {words = "adana ani", name = "paralyze rune", group1 = "support", group2 = "", type = "rune", vocation = "elder druid", cooldown = 2, duration = 1, level = 54, mp = 1400, premium = true, soul = 3, mlevel = 18, condition = "7"},
  777.         {words = "adana mort", name = "animate dead rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 27, mp = 600, premium = true, soul = 5, mlevel = 4, condition = "1"},
  778.         {words = "adana pox", name = "cure poison rune", group1 = "support", group2 = "", type = "rune", vocation = "druid", cooldown = 2, duration = 1, level = 15, mp = 200, premium = false, soul = 1, mlevel = 0, condition = "7"},
  779.         {words = "adeta sio", name = "convince creature rune", group1 = "support", group2 = "", type = "rune", vocation = "druid", cooldown = 2, duration = 1, level = 16, mp = 200, premium = false, soul = 3, mlevel = 5, condition = "7"},
  780.         {words = "adevo grav flam", name = "fire field rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 15, mp = 240, premium = false, soul = 1, mlevel = 1, condition = "7"},
  781.         {words = "adevo grav pox", name = "poison field rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 14, mp = 200, premium = false, soul = 1, mlevel = 0, condition = "7"},
  782.         {words = "adevo grav tera", name = "magic wall rune", group1 = "support", group2 = "", type = "rune", vocation = "master sorcerer", cooldown = 2, duration = 1, level = 32, mp = 750, premium = true, soul = 5, mlevel = 9, condition = "7"},
  783.         {words = "adevo grav vis", name = "energy field rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 18, mp = 320, premium = false, soul = 2, mlevel = 3, condition = "7"},
  784.         {words = "adevo grav vita", name = "wild growth rune", group1 = "support", group2 = "", type = "rune", vocation = "elder druid", cooldown = 2, duration = 1, level = 27, mp = 600, premium = true, soul = 5, mlevel = 8, condition = "7"},
  785.         {words = "adevo ina", name = "chameleon rune", group1 = "support", group2 = "", type = "rune", vocation = "druid", cooldown = 2, duration = 1, level = 27, mp = 600, premium = false, soul = 2, mlevel = 4, condition = "7"},
  786.         {words = "adevo mas flam", name = "fire bomb rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 27, mp = 600, premium = false, soul = 4, mlevel = 5, condition = "1x1"},
  787.         {words = "adevo mas grav flam", name = "fire wall rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 33, mp = 780, premium = false, soul = 4, mlevel = 6, condition = "7"},
  788.         {words = "adevo mas grav pox", name = "poison wall rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 29, mp = 640, premium = false, soul = 3, mlevel = 5, condition = "7"},
  789.         {words = "adevo mas grav vis", name = "energy wall rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 41, mp = 1000, premium = false, soul = 5, mlevel = 9, condition = "7"},
  790.         {words = "adevo mas hur", name = "explosion rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 31, mp = 570, premium = false, soul = 4, mlevel = 6, condition = "explo"},
  791.         {words = "adevo mas pox", name = "poison bomb rune", group1 = "support", group2 = "", type = "rune", vocation = "elder druid", cooldown = 2, duration = 1, level = 25, mp = 520, premium = true, soul = 2, mlevel = 4, condition = "7"},
  792.         {words = "adevo mas vis", name = "energy bomb rune", group1 = "support", group2 = "", type = "rune", vocation = "master sorcerer", cooldown = 2, duration = 1, level = 37, mp = 880, premium = true, soul = 5, mlevel = 10, condition = "1x1"},
  793.         {words = "adevo res flam", name = "soulfire rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 27, mp = 420, premium = true, soul = 3, mlevel = 7, condition = "7"},
  794.         {words = "adito grav", name = "destroy field rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 17, mp = 120, premium = false, soul = 2, mlevel = 3, condition = "7"},
  795.         {words = "adito tera", name = "desintegrate rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 21, mp = 200, premium = true, soul = 3, mlevel = 4, condition = "1"},
  796.         {words = "adori flam", name = "fireball rune", group1 = "support", group2 = "", type = "rune", vocation = "master sorcerer", cooldown = 2, duration = 1, level = 27, mp = 460, premium = true, soul = 3, mlevel = 4, condition = "7"},
  797.         {words = "adori frigo", name = "icicle rune", group1 = "support", group2 = "", type = "rune", vocation = "elder druid", cooldown = 2, duration = 1, level = 28, mp = 460, premium = true, soul = 3, mlevel = 4, condition = "7"},
  798.         {words = "adori gran mort", name = "sudden death rune", group1 = "support", group2 = "", type = "rune", vocation = "sorcerer", cooldown = 2, duration = 1, level = 45, mp = 985, premium = false, soul = 5, mlevel = 15, condition = "7"},
  799.         {words = "adori mas flam", name = "great fireball rune", group1 = "support", group2 = "", type = "rune", vocation = "sorcerer", cooldown = 2, duration = 1, level = 30, mp = 530, premium = false, soul = 3, mlevel = 4, condition = "3x3"},
  800.         {words = "adori mas frigo", name = "avalanche rune", group1 = "support", group2 = "", type = "rune", vocation = "druid", cooldown = 2, duration = 1, level = 30, mp = 530, premium = false, soul = 3, mlevel = 4, condition = "3x3"},
  801.         {words = "adori mas tera", name = "stone shower rune", group1 = "support", group2 = "", type = "rune", vocation = "elder druid", cooldown = 2, duration = 1, level = 28, mp = 430, premium = true, soul = 3, mlevel = 4, condition = "3x3"},
  802.         {words = "adori mas vis", name = "thunderstorm rune", group1 = "support", group2 = "", type = "rune", vocation = "master sorcerer", cooldown = 2, duration = 1, level = 28, mp = 430, premium = true, soul = 3, mlevel = 4, condition = "3x3"},
  803.         {words = "adori min vis", name = "light magic missile rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 15, mp = 120, premium = false, soul = 1, mlevel = 0, condition = "7"},
  804.         {words = "adori san", name = "holy missile rune", group1 = "support", group2 = "", type = "rune", vocation = "royal palafireball runedin", cooldown = 2, duration = 1, level = 27, mp = 300, premium = true, soul = 3, mlevel = 4, condition = "7"},
  805.         {words = "adori tera", name = "stalagmite rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 24, mp = 350, premium = false, soul = 2, mlevel = 3, condition = "7"},
  806.         {words = "adori vis", name = "heavy magic missile rune", group1 = "support", group2 = "", type = "rune", vocation = false, cooldown = 2, duration = 1, level = 25, mp = 350, premium = false, soul = 2, mlevel = 3, condition = "7"},
  807.         {words = "adura gran", name = "intense healing rune", group1 = "support", group2 = "", type = "rune", vocation = "druid", cooldown = 2, duration = 1, level = 15, mp = 120, premium = false, soul = 2, mlevel = 1, condition = "7"},
  808.         {words = "adura vita", name = "ultimate healing rune", group1 = "support", group2 = "", type = "rune", vocation = "druid", cooldown = 2, duration = 1, level = 24, mp = 400, premium = false, soul = 3, mlevel = 4, condition = "7"},
  809.         {words = "exana flam", name = "cure burning", group1 = "healing", group2 = "", type = "instant", vocation = "elder druid", cooldown = 6, duration = 1, level = 30, mp = 30, premium = true, soul = 0, mlevel = 0, condition = ""},
  810.         {words = "exana ina", name = "cancel invisibility", group1 = "support", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 1, level = 26, mp = 200, premium = true, soul = 0, mlevel = 0, condition = ""},
  811.         {words = "exana kor", name = "cure bleeding", group1 = "healing", group2 = "", type = "instant", vocation = false, cooldown = 6, duration = 1, level = 45, mp = 30, premium = true, soul = 0, mlevel = 0, condition = ""},
  812.         {words = "exana mort", name = "cure curse", group1 = "healing", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 6, duration = 1, level = 80, mp = 40, premium = true, soul = 0, mlevel = 0, condition = ""},
  813.         {words = "exana pox", name = "cure poison", group1 = "healing", group2 = "", type = "instant", vocation = false, cooldown = 1, duration = 1, level = 10, mp = 30, premium = false, soul = 0, mlevel = 0, condition = ""},
  814.         {words = "exana vis", name = "cure electrification", group1 = "healing", group2 = "", type = "instant", vocation = "elder druid", cooldown = 6, duration = 1, level = 22, mp = 30, premium = true, soul = 0, mlevel = 0, condition = ""},
  815.         {words = "exani hur", name = "levitate", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 1, level = 12, mp = 50, premium = true, soul = 0, mlevel = 0, condition = "word"},
  816.         {words = "exani tera", name = "magic rope", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 1, level = 9, mp = 20, premium = true, soul = 0, mlevel = 0, condition = ""},
  817.         {words = "exeta con", name = "enchant spear", group1 = "support", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 1, level = 45, mp = 350, premium = true, soul = 0, mlevel = 0, condition = ""},
  818.         {words = "exeta res", name = "challenge", group1 = "support", group2 = "", type = "instant", vocation = "elite knight", cooldown = 2, duration = 1, level = 20, mp = 30, premium = true, soul = 0, mlevel = 0, condition = "1x1"},
  819.         {words = "exeta vis", name = "enchant staff", group1 = "support", group2 = "", type = "instant", vocation = "master sorcerer", cooldown = 2, duration = 1, level = 41, mp = 80, premium = true, soul = 0, mlevel = 0, condition = ""},
  820.         {words = "exevo con", name = "conjure arrow", group1 = "support", group2 = "", type = "instant", vocation = "paladin", cooldown = 2, duration = 1, level = 13, mp = 100, premium = false, soul = 0, mlevel = 0, condition = ""},
  821.         {words = "exevo con flam", name = "conjure explosive arrow", group1 = "support", group2 = "", type = "instant", vocation = "paladin", cooldown = 2, duration = 1, level = 25, mp = 290, premium = false, soul = 0, mlevel = 0, condition = ""},
  822.         {words = "exevo con grav", name = "conjure piercing bolt", group1 = "support", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 1, level = 33, mp = 180, premium = true, soul = 0, mlevel = 0, condition = ""},
  823.         {words = "exevo con hur", name = "conjure sniper arrow", group1 = "support", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 1, level = 24, mp = 160, premium = true, soul = 0, mlevel = 0, condition = ""},
  824.         {words = "exevo con mort", name = "conjure bolt", group1 = "support", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 1, level = 17, mp = 140, premium = true, soul = 0, mlevel = 0, condition = ""},
  825.         {words = "exevo con pox", name = "conjure poisoned arrow", group1 = "support", group2 = "", type = "instant", vocation = "paladin", cooldown = 2, duration = 1, level = 16, mp = 130, premium = false, soul = 0, mlevel = 0, condition = ""},
  826.         {words = "exevo con vis", name = "conjure power bolt", group1 = "support", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 1, level = 59, mp = 700, premium = true, soul = 0, mlevel = 0, condition = ""},
  827.         {words = "exevo flam hur", name = "fire wave", group1 = "attack", group2 = "", type = "instant", vocation = "sorcerer", cooldown = 4, duration = 1, level = 18, mp = 25, premium = false, soul = 0, mlevel = 0, condition = "smallwave"},
  828.         {words = "exevo frigo hur", name = "ice wave", group1 = "attack", group2 = "", type = "instant", vocation = "druid", cooldown = 4, duration = 1, level = 18, mp = 25, premium = false, soul = 0, mlevel = 0, condition = "smallwave"},
  829.         {words = "exevo gran frigo hur", name = "strong ice wave", group1 = "attack", group2 = "", type = "instant", vocation = "elder druid", cooldown = 8, duration = 1, level = 40, mp = 170, premium = true, soul = 0, mlevel = 0, condition = "smallwave"},
  830.         {words = "exevo gran mas flam", name = "hells core", group1 = "attack", group2 = "", type = "instant", vocation = "master sorcerer", cooldown = 40, duration = 1, level = 60, mp = 1100, premium = true, soul = 0, mlevel = 0, condition = "5x5"},
  831.         {words = "exevo gran mas frigo", name = "eternal winter", group1 = "attack", group2 = "", type = "instant", vocation = "elder druid", cooldown = 40, duration = 1, level = 60, mp = 1050, premium = true, soul = 0, mlevel = 0, condition = "5x5"},
  832.         {words = "exevo gran mas tera", name = "wrath of nature", group1 = "attack", group2 = "", type = "instant", vocation = "elder druid", cooldown = 40, duration = 1, level = 55, mp = 700, premium = true, soul = 0, mlevel = 0, condition = "6x6"},
  833.         {words = "exevo gran mas vis", name = "rage of the skies", group1 = "attack", group2 = "", type = "instant", vocation = "master sorcerer", cooldown = 40, duration = 1, level = 55, mp = 600, premium = true, soul = 0, mlevel = 0, condition = "6x6"},
  834.         {words = "exevo gran vis lux", name = "great energy beam", group1 = "attack", group2 = "", type = "instant", vocation = "sorcerer", cooldown = 6, duration = 1, level = 29, mp = 110, premium = false, soul = 0, mlevel = 0, condition = "bigbeam"},
  835.         {words = "exevo mas san", name = "divine caldera", group1 = "attack", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 4, duration = 1, level = 50, mp = 160, premium = true, soul = 0, mlevel = 0, condition = "3x3"},
  836.         {words = "exevo pan", name = "food", group1 = "support", group2 = "", type = "instant", vocation = "druid", cooldown = 2, duration = 1, level = 14, mp = 120, premium = false, soul = 0, mlevel = 0, condition = ""},
  837.         {words = "exevo tera hur", name = "terra wave", group1 = "attack", group2 = "", type = "instant", vocation = "druid", cooldown = 4, duration = 1, level = 38, mp = 210, premium = false, soul = 0, mlevel = 0, condition = "bigwave"},
  838.         {words = "exevo vis hur", name = "energy wave", group1 = "attack", group2 = "", type = "instant", vocation = "sorcerer", cooldown = 8, duration = 1, level = 38, mp = 170, premium = false, soul = 0, mlevel = 0, condition = "bigwave"},
  839.         {words = "exevo vis lux", name = "energy beam", group1 = "attack", group2 = "", type = "instant", vocation = "sorcerer", cooldown = 4, duration = 1, level = 23, mp = 40, premium = false, soul = 0, mlevel = 0, condition = "smallbeam"},
  840.         {words = "exiva", name = "find person", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 1, level = 8, mp = 20, premium = false, soul = 0, mlevel = 0, condition = "word"},
  841.         {words = "exori", name = "berserk", group1 = "attack", group2 = "", type = "instant", vocation = "elite knight", cooldown = 4, duration = 1, level = 35, mp = 115, premium = true, soul = 0, mlevel = 0, condition = "1x1"},
  842.         {words = "exori amp vis", name = "lightning", group1 = "attack", group2 = "special", type = "instant", vocation = "master sorcerer", cooldown = 8, duration = 1, level = 55, mp = 60, premium = true, soul = 0, mlevel = 0, condition = "5"},
  843.         {words = "exori con", name = "ethereal spear", group1 = "attack", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 1, level = 23, mp = 25, premium = true, soul = 0, mlevel = 0, condition = "7"},
  844.         {words = "exori flam", name = "flame strike", group1 = "attack", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 1, level = 14, mp = 20, premium = true, soul = 0, mlevel = 0, condition = "3"},
  845.         {words = "exori frigo", name = "ice strike", group1 = "attack", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 1, level = 15, mp = 20, premium = true, soul = 0, mlevel = 0, condition = "3"},
  846.         {words = "exori gran", name = "fierce berserk", group1 = "attack", group2 = "", type = "instant", vocation = "elite knight", cooldown = 6, duration = 1, level = 90, mp = 340, premium = true, soul = 0, mlevel = 0, condition = "1x1"},
  847.         {words = "exori gran con", name = "strong ethereal spear", group1 = "attack", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 8, duration = 1, level = 90, mp = 55, premium = true, soul = 0, mlevel = 0, condition = "7"},
  848.         {words = "exori gran flam", name = "strong flame strike", group1 = "attack", group2 = "special", type = "instant", vocation = "master sorcerer", cooldown = 8, duration = 1, level = 70, mp = 60, premium = true, soul = 0, mlevel = 0, condition = "3"},
  849.         {words = "exori gran frigo", name = "strong ice strike", group1 = "attack", group2 = "special", type = "instant", vocation = "elder druid", cooldown = 8, duration = 1, level = 80, mp = 60, premium = true, soul = 0, mlevel = 0, condition = "3"},
  850.         {words = "exori gran ico", name = "annihilation", group1 = "attack", group2 = "", type = "instant", vocation = "elite knight", cooldown = 30, duration = 1, level = 110, mp = 300, premium = true, soul = 0, mlevel = 0, condition = "5"},
  851.         {words = "exori gran tera", name = "strong terra strike", group1 = "attack", group2 = "special", type = "instant", vocation = "elder druid", cooldown = 8, duration = 1, level = 70, mp = 60, premium = true, soul = 0, mlevel = 0, condition = "3"},
  852.         {words = "exori gran vis", name = "strong energy strike", group1 = "attack", group2 = "special", type = "instant", vocation = "master sorcerer", cooldown = 8, duration = 1, level = 80, mp = 60, premium = true, soul = 0, mlevel = 0, condition = "3"},
  853.         {words = "exori hur", name = "whirlwind throw", group1 = "attack", group2 = "", type = "instant", vocation = "elite knight", cooldown = 6, duration = 1, level = 28, mp = 40, premium = true, soul = 0, mlevel = 0, condition = "5"},
  854.         {words = "exori ico", name = "brutal strike", group1 = "attack", group2 = "", type = "instant", vocation = "elite knight", cooldown = 6, duration = 1, level = 16, mp = 30, premium = true, soul = 0, mlevel = 0, condition = "1"},
  855.         {words = "exori mas", name = "groundshaker", group1 = "attack", group2 = "", type = "instant", vocation = "elite knight", cooldown = 8, duration = 1, level = 33, mp = 160, premium = true, soul = 0, mlevel = 0, condition = "3x3"},
  856.         {words = "exori max flam", name = "ultimate flame strike", group1 = "attack", group2 = "", type = "instant", vocation = "master sorcerer", cooldown = 30, duration = 1, level = 90, mp = 100, premium = true, soul = 0, mlevel = 0, condition = "3"},
  857.         {words = "exori max frigo", name = "ultimate ice strike", group1 = "attack", group2 = "", type = "instant", vocation = "elder druid", cooldown = 30, duration = 1, level = 100, mp = 100, premium = true, soul = 0, mlevel = 0, condition = "3"},
  858.         {words = "exori max tera", name = "ultimate terra strike", group1 = "attack", group2 = "", type = "instant", vocation = "elder druid", cooldown = 30, duration = 1, level = 90, mp = 100, premium = true, soul = 0, mlevel = 0, condition = "3"},
  859.         {words = "exori max vis", name = "ultimate energy strike", group1 = "attack", group2 = "", type = "instant", vocation = "master sorcerer", cooldown = 30, duration = 1, level = 100, mp = 100, premium = true, soul = 0, mlevel = 0, condition = "3"},
  860.         {words = "exori min", name = "front sweep", group1 = "attack", group2 = "", type = "instant", vocation = "elite knight", cooldown = 6, duration = 1, level = 70, mp = 200, premium = true, soul = 0, mlevel = 0, condition = "front"},
  861.         {words = "exori moe ico", name = "physical strike", group1 = "attack", group2 = "", type = "instant", vocation = "elder druid", cooldown = 2, duration = 1, level = 16, mp = 20, premium = true, soul = 0, mlevel = 0, condition = "3"},
  862.         {words = "exori mort", name = "death strike", group1 = "attack", group2 = "", type = "instant", vocation = "master sorcerer", cooldown = 2, duration = 1, level = 16, mp = 20, premium = true, soul = 0, mlevel = 0, condition = "3"},
  863.         {words = "exori san", name = "divine missile", group1 = "attack", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 1, level = 40, mp = 20, premium = true, soul = 0, mlevel = 0, condition = "4"},
  864.         {words = "exori tera", name = "terra strike", group1 = "attack", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 1, level = 13, mp = 20, premium = true, soul = 0, mlevel = 0, condition = "3"},
  865.         {words = "exori vis", name = "energy strike", group1 = "attack", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 1, level = 12, mp = 20, premium = true, soul = 0, mlevel = 0, condition = "3"},
  866.         {words = "exura", name = "light healing", group1 = "healing", group2 = "", type = "instant", vocation = false, cooldown = 1, duration = 1, level = 9, mp = 20, premium = false, soul = 0, mlevel = 0, condition = ""},
  867.         {words = "exura gran", name = "intense healing", group1 = "healing", group2 = "", type = "instant", vocation = false, cooldown = 1, duration = 1, level = 11, mp = 70, premium = false, soul = 0, mlevel = 0, condition = ""},
  868.         {words = "exura gran ico", name = "intense wound cleansing", group1 = "healing", group2 = "", type = "instant", vocation = "elite knight", cooldown = 600, duration = 1, level = 80, mp = 200, premium = true, soul = 0, mlevel = 0, condition = ""},
  869.         {words = "exura gran mas res", name = "mass healing", group1 = "healing", group2 = "", type = "instant", vocation = "elder druid", cooldown = 2, duration = 1, level = 36, mp = 150, premium = true, soul = 0, mlevel = 0, condition = "3x3"},
  870.         {words = "exura gran san", name = "salvation", group1 = "healing", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 1, duration = 1, level = 60, mp = 210, premium = true, soul = 0, mlevel = 0, condition = ""},
  871.         {words = "exura ico", name = "wound cleansing", group1 = "healing", group2 = "", type = "instant", vocation = "knight", cooldown = 1, duration = 1, level = 10, mp = 40, premium = false, soul = 0, mlevel = 0, condition = ""},
  872.         {words = "exura san", name = "divine healing", group1 = "healing", group2 = "", type = "instant", vocation = "paladin", cooldown = 1, duration = 1, level = 35, mp = 160, premium = false, soul = 0, mlevel = 0, condition = ""},
  873.         {words = "exura sio", name = "heal friend", group1 = "healing", group2 = "", type = "instant", vocation = "elder druid", cooldown = 1, duration = 1, level = 18, mp = 140, premium = true, soul = 0, mlevel = 0, condition = "word"},
  874.         {words = "exura vita", name = "ultimate healing", group1 = "healing", group2 = "", type = "instant", vocation = false, cooldown = 1, duration = 1, level = 20, mp = 160, premium = false, soul = 0, mlevel = 0, condition = ""},
  875.         {words = "utamo mas sio", name = "protect party", group1 = "support", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 120, level = 32, mp = 0, premium = true, soul = 0, mlevel = 0, condition = "3x3"},
  876.         {words = "utamo tempo", name = "protector", group1 = "support", group2 = "", type = "instant", vocation = "elite knight", cooldown = 2, duration = 10, level = 55, mp = 200, premium = true, soul = 0, mlevel = 0, condition = ""},
  877.         {words = "utamo tempo san", name = "swift foot", group1 = "support", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 10, level = 55, mp = 400, premium = true, soul = 0, mlevel = 0, condition = ""},
  878.         {words = "utamo vita", name = "magic shield", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 200, level = 14, mp = 50, premium = false, soul = 0, mlevel = 0, condition = ""},
  879.         {words = "utana vid", name = "invisible", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 200, level = 35, mp = 440, premium = false, soul = 0, mlevel = 0, condition = ""},
  880.         {words = "utani gran hur", name = "strong haste", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 8, duration = 22, level = 20, mp = 100, premium = true, soul = 0, mlevel = 0, condition = ""},
  881.         {words = "utani hur", name = "haste", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 30, level = 14, mp = 60, premium = true, soul = 0, mlevel = 0, condition = ""},
  882.         {words = "utani tempo hur", name = "charge", group1 = "support", group2 = "", type = "instant", vocation = "elite knight", cooldown = 2, duration = 5, level = 25, mp = 100, premium = true, soul = 0, mlevel = 0, condition = ""},
  883.         {words = "utevo gran lux", name = "great light", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 695, level = 13, mp = 60, premium = false, soul = 0, mlevel = 0, condition = ""},
  884.         {words = "utevo lux", name = "light", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 370, level = 8, mp = 20, premium = false, soul = 0, mlevel = 0, condition = ""},
  885.         {words = "utevo res", name = "summon creature", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 1, level = 25, mp = 0, premium = false, soul = 0, mlevel = 0, condition = "word"},
  886.         {words = "utevo res ina", name = "creature illusion", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 1, level = 23, mp = 100, premium = false, soul = 0, mlevel = 0, condition = "word"},
  887.         {words = "utevo vis lux", name = "ultimate light", group1 = "support", group2 = "", type = "instant", vocation = false, cooldown = 2, duration = 1980, level = 26, mp = 140, premium = true, soul = 0, mlevel = 0, condition = ""},
  888.         {words = "utito mas sio", name = "train party", group1 = "support", group2 = "", type = "instant", vocation = "elite knight", cooldown = 2, duration = 120, level = 32, mp = 0, premium = true, soul = 0, mlevel = 0, condition = "3x3"},
  889.         {words = "utito tempo", name = "blood rage", group1 = "support", group2 = "", type = "instant", vocation = "elite knight", cooldown = 2, duration = 10, level = 60, mp = 290, premium = true, soul = 0, mlevel = 0, condition = ""},
  890.         {words = "utito tempo san", name = "sharpshooter", group1 = "support", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 2, duration = 10, level = 60, mp = 450, premium = true, soul = 0, mlevel = 0, condition = ""},
  891.         {words = "utori flam", name = "ignite", group1 = "attack", group2 = "", type = "instant", vocation = "master sorcerer", cooldown = 30, duration = 1, level = 26, mp = 30, premium = true, soul = 0, mlevel = 0, condition = "3"},
  892.         {words = "utori kor", name = "inflict wound", group1 = "attack", group2 = "", type = "instant", vocation = "elite knight", cooldown = 30, duration = 1, level = 40, mp = 30, premium = true, soul = 0, mlevel = 0, condition = "3"},
  893.         {words = "utori mas sio", name = "enchant party", group1 = "support", group2 = "", type = "instant", vocation = "master sorcerer", cooldown = 2, duration = 120, level = 32, mp = 0, premium = true, soul = 0, mlevel = 0, condition = "3x3"},
  894.         {words = "utori mort", name = "curse", group1 = "attack", group2 = "", type = "instant", vocation = "master sorcerer", cooldown = 50, duration = 1, level = 75, mp = 30, premium = true, soul = 0, mlevel = 0, condition = "3"},
  895.         {words = "utori pox", name = "envenom", group1 = "attack", group2 = "", type = "instant", vocation = "elder druid", cooldown = 30, duration = 1, level = 50, mp = 30, premium = true, soul = 0, mlevel = 0, condition = "3"},
  896.         {words = "utori san", name = "holy flash", group1 = "attack", group2 = "", type = "instant", vocation = "royal paladin", cooldown = 40, duration = 1, level = 70, mp = 50, premium = true, soul = 0, mlevel = 0, condition = "3"},
  897.         {words = "utori vis", name = "electrify", group1 = "attack", group2 = "", type = "instant", vocation = "master sorcerer", cooldown = 1, duration = 1, level = 34, mp = 30, premium = true, soul = 0, mlevel = 0, condition = "3"},
  898.         {words = "utura", name = "recovery", group1 = "healing", group2 = "", type = "instant", vocation = false, cooldown = 60, duration = 60, level = 50, mp = 75, premium = true, soul = 0, mlevel = 0, condition = ""},
  899.         {words = "utura gran", name = "intense recovery", group1 = "healing", group2 = "", type = "instant", vocation = false, cooldown = 60, duration = 60, level = 100, mp = 165, premium = true, soul = 0, mlevel = 0, condition = ""},
  900.         {words = "utura mas sio", name = "heal party", group1 = "support", group2 = "", type = "instant", vocation = "elder druid", cooldown = 2, duration = 120, level = 32, mp = 0, premium = true, soul = 0, mlevel = 0, condition = "3x3"}
  901.     }
  902. }
  903.  
  904. function Spell:getInfo(spell_name, search_type) -- Working
  905.     arguments('Spell:getInfo', {'string', spell_name})
  906.  
  907.     local spell_found
  908.     if ((search_type or ''):lower() == 'words') then
  909.         spell_found = table.binaryfind(self.data, spell_name:lower(), 'words')
  910.     elseif ((search_type or ''):lower() == 'name') then
  911.         spell_found = table.find(self.data, spell_name:lower(), 'name')
  912.     else
  913.         spell_found = table.binaryfind(self.data, spell_name:lower(), 'words') or table.find(self.data, spell_name:lower(), 'name')
  914.     end
  915.  
  916.     if (spell_found) then
  917.         return self.data[spell_found]
  918.     end
  919.  
  920.     return nil
  921. end
  922.  
  923. Untils = {
  924. }
  925.  
  926. function Untils:parseLootMessage(message, with_amount) -- Working
  927.     if (type(message) == 'userdata') then message = message.content end
  928.     if (type(with_amount) ~= 'boolean') then with_amount = false end
  929.     if (not string.find(message:lower(), 'loot of')) then return end
  930.  
  931.     arguments('Untils:getMonsterLoot', {'string', message, 'boolean', with_amount})
  932.  
  933.     local loot_info, exceptions = {name = '', items = {}}, {['small rubies'] = 'small ruby', ['small topazes'] = 'small topaz', ['giant shimmering pearl'] = 'giant shimmering pearl (blue)'}
  934.  
  935.     loot_info.name, loot_info.items_temp = message:match('Loot of[ an]* (.+): (.+)')
  936.     if (loot_info.name) then
  937.         for _, item in ipairs(loot_info.items_temp:token(nil, ', ')) do
  938.             setwarning(WARNING_ITEM, false)
  939.  
  940.             local item_amount = tonumber(item:token(1)) or 1
  941.             local _item_name = item:gsub('%d', ''):gsub('^a ', ''):gsub('^an ', ''):gsub('^[%s]*', ''):lower()
  942.            
  943.             if (exceptions[_item_name] ~= nil) then
  944.                 _item_name = exceptions[_item_name]
  945.             end
  946.            
  947.             local item_name = itemname(itemid(_item_name))
  948.  
  949.             if (#item_name ~= 0) then
  950.                 if (with_amount) then
  951.                     local item_found = table.find(loot_info.items, item_name, 'name')
  952.  
  953.                     if (item_found) then
  954.                         loot_info.items[item_found].amount = loot_info.items[item_found].amount + item_amount
  955.                     else
  956.                         table.insert(loot_info.items, {name = item_name, amount = item_amount})
  957.                     end
  958.                 elseif (not table.find(loot_info.items, item_name)) then
  959.                     table.insert(loot_info.items, item_name)
  960.                 end
  961.             end
  962.         end
  963.  
  964.         loot_info.items_temp = nil
  965.  
  966.         return loot_info
  967.     end
  968.  
  969.     return {name = '', items = {}}
  970. end
  971.  
  972. function Untils:parseAttackMessage(message) -- Working
  973.     if (type(message) == 'userdata') then message = message.content end
  974.     if (not string.find(message, 'lose')) then return end
  975.  
  976.     arguments('Untils:parseAttackMessage', {'string', message})
  977.  
  978.     local damage_info = {damage = 0, dealer = {name = '', type = ''}, target = {name = '', type = ''}}
  979.  
  980.     damage_info.damage, damage_info.dealer.name = message:match('You lose (%w+) .+ due to an attack by (.+)%.')
  981.     if (damage_info.damage) then
  982.         damage_info.damage = tonumber(damage_info.damage)
  983.         damage_info.dealer.name = damage_info.dealer.name:gsub('^a ', ''):gsub('^an ', '')
  984.         damage_info.dealer.type = (Unit:isPlayer(damage_info.dealer.name) and ('player')) or ('monster')
  985.         damage_info.target = {name = $name, type = 'player'}
  986.  
  987.         return damage_info
  988.     else
  989.         damage_info.target.name, damage_info.damage = message:match('(.+) loses (%w+) .+ due to your attack%.')
  990.         if (damage_info.damage) then
  991.             damage_info.damage = tonumber(damage_info.damage)
  992.             damage_info.dealer = {name = $name, type = 'player'}
  993.             damage_info.target.name = damage_info.target.name:gsub('^A ', ''):gsub('^An ', '')
  994.             damage_info.target.type = (Unit:isPlayer(damage_info.target.name) and ('player')) or ('monster')
  995.  
  996.             return damage_info
  997.         else
  998.             damage_info.target.name, damage_info.damage, damage_info.dealer.name = message:match('(.+) loses (%w+) .+ due to an attack by (.+)%.')
  999.             if (damage_info.damage) then
  1000.                 damage_info.damage = tonumber(damage_info.damage)
  1001.                 damage_info.dealer.name = damage_info.dealer.name:gsub('^a ', ''):gsub('^an ', '')
  1002.                 damage_info.dealer.type = (Unit:isPlayer(damage_info.dealer.name) and ('player')) or ('monster')
  1003.                 damage_info.target.name = damage_info.target.name:gsub('^A ', ''):gsub('^An ', '')
  1004.                 damage_info.target.type = (Unit:isPlayer(damage_info.target.name) and ('player')) or ('monster')
  1005.  
  1006.                 return damage_info
  1007.             end
  1008.         end
  1009.     end
  1010.  
  1011.     return {damage = 0, dealer = {name = '', type = ''}, target = {name = '', type = ''}}
  1012. end
  1013.  
  1014. function Untils:parseHealMessage(message) -- Working
  1015.     if (type(message) == 'userdata') then message = message.content end
  1016.     if (not string.find(message, 'heal')) then return end
  1017.  
  1018.     arguments('Untils:parseHealMessage', {'string', message})
  1019.  
  1020.     local heal_info = {damage = 0, healer = '', target = ''}
  1021.  
  1022.     heal_info.damage = message:match('You healed yourself for (%w+) hitpoint[s]*%.')
  1023.     if (heal_info.damage) then
  1024.         heal_info.damage, heal_info.healer, heal_info.target = tonumber(heal_info.damage), $name, $name
  1025.  
  1026.         return heal_info
  1027.     else
  1028.         heal_info.healer, heal_info.damage = message:match('(.+) healed himself for (%w+) hitpoint[s]*%.')
  1029.         if (heal_info.damage) then
  1030.             heal_info.damage, heal_info.target = tonumber(heal_info.damage), heal_info.healer
  1031.  
  1032.             return heal_info
  1033.         else
  1034.             heal_info.target, heal_info.damage = message:match('You heal (.+) for (%w+) hitpoint[s]*%.')
  1035.             if (heal_info.damage) then
  1036.                 heal_info.damage, heal_info.healer = tonumber(heal_info.damage), $name
  1037.  
  1038.                 return heal_info
  1039.             else
  1040.                 heal_info.healer, heal_info.damage= message:match('You were healed by (.+) for (%w+) hitpoint[s]*%.')
  1041.                 if (heal_info.damage) then
  1042.                     heal_info.damage, heal_info.target = tonumber(heal_info.damage), $name
  1043.  
  1044.                     return heal_info
  1045.                 else
  1046.                     heal_info.target, heal_info.healer, heal_info.damage = message:match('(.+) was healed by (.+) for (%w+) hitpoint[s]*%.')
  1047.                     if (heal_info.damage) then
  1048.                         heal_info.damage = tonumber(heal_info.damage)
  1049.  
  1050.                         return heal_info
  1051.                     end
  1052.                 end
  1053.             end
  1054.         end
  1055.     end
  1056.  
  1057.     return {damage = 0, healer = '', target = ''}
  1058. end
  1059.  
  1060. function Untils:string2Pixels(text) -- Working
  1061.     if (type(text) ~= 'string') then text = tostring(text) end
  1062.  
  1063.     local pixels = 0
  1064.     local characters = {[" "] = 3, ["!"] = 3, ['"'] = 6, ["#"] = 9, ["$"] = 7, ["%"] = 12, ["&"] = 9, ["'"] = 3, ["("] = 5, [")"] = 5, ["*"] = 6, [","] = 4, ["-"] = 5, ["."] = 3, ["/"] = 6, ["0"] = 7, ["1"] = 7, ["2"] = 7, ["3"] = 7, ["4"] = 7, ["5"] = 7, ["6"] = 7, ["7"] = 7, ["8"] = 7, ["9"] = 7, [":"] = 3, [";"] = 3, ["<"] = 9, ["="] = 9, [">"] = 9, ["?"] = 6, ["@"] = 10, ["A"] = 9, ["B"] = 7, ["C"] = 7, ["D"] = 8, ["E"] = 6, ["F"] = 6, ["G"] = 8, ["H"] = 8, ["I"] = 5, ["J"] = 6, ["K"] = 7, ["L"] = 6, ["M"] = 10, ["N"] = 7, ["O"] = 8, ["P"] = 7, ["Q"] = 8, ["R"] = 8, ["S"] = 7, ["T"] = 7, ["U"] = 8, ["V"] = 7, ["X"] = 7, ["W"] = 11, ["Y"] = 7, ["Z"] = 7, ["["] = 5, ["\\"] = 6, ["]"] = 5, ["^"] = 9, ["_"] = 7, ["`"] = 6, ["a"] = 7, ["b"] = 7, ["c"] = 6, ["d"] = 7, ["e"] = 7, ["f"] = 4, ["g"] = 7, ["h"] = 7, ["i"] = 3, ["j"] = 4, ["k"] = 7, ["l"] = 3, ["m"] = 11, ["n"] = 7, ["o"] = 7, ["p"] = 7, ["q"] = 7, ["r"] = 5, ["s"] = 6, ["t"] = 5, ["u"] = 7, ["v"] = 7, ["x"] = 7, ["w"] = 9, ["y"] = 7, ["z"] = 6, ["{"] = 7, ["|"] = 7, ["}"] = 7, ["~"] = 9}
  1065.  
  1066.     if (#text ~= 0) then
  1067.         for i = 1, #text do
  1068.             pixels = pixels + (characters[string.sub(text, i, i)] or 0)
  1069.         end
  1070.     end
  1071.  
  1072.     return pixels
  1073. end
  1074.  
  1075. local STATS_DATA_RUN_LAST = $timems
  1076. local STATS_DATA_RUN_DELAY = 100
  1077.  
  1078. Stats = {
  1079.     monsters_seen = {},
  1080.     players_seen = {},
  1081.     monsters_killed = {},
  1082.     items_looted = {},
  1083.     supplies_used = {},
  1084.     damage_dealt = 0,
  1085.     damage_received = 0,
  1086.     damage_stats = {},
  1087.     heal_stats = {}
  1088. }
  1089.  
  1090. function Stats:getGamePlayData() -- Working
  1091.     if (STATS_DATA_RUN_LAST + STATS_DATA_RUN_DELAY >= $timems) then return end
  1092.    
  1093.     if (#self.supplies_used == 0) then
  1094.         for _, section in ipairs({'POTIONS_AND_RUNES', 'AMMUNITION', 'DISTANCE_WEAPONS'}) do
  1095.             for _, section_item in ipairs(exec('return ' .. section)) do
  1096.                 table.binaryinsert(self.supplies_used, {name = section_item, id = itemid(section_item), type = section, current_amount = (section == 'POTIONS_AND_RUNES' and servercount(section_item)) or (section == 'AMMUNITION' and itemcount(section_item, 'belt')) or (section == 'DISTANCE_WEAPONS' and itemcount(section_item, 'rhand')) or 0, amount = 0, price = math.positive(itemcost(section_item))}, 'name')
  1097.             end
  1098.         end
  1099.     end
  1100.  
  1101.     for _, supply in ipairs(self.supplies_used) do
  1102.         if (supply.type == 'POTIONS_AND_RUNES') then
  1103.             if (servercount(supply.name) ~= supply.current_amount) then
  1104.                 supply.current_amount, supply.amount = servercount(supply.name), supply.amount + 1
  1105.             end
  1106.         elseif (supply.type == 'AMMUNITION') then
  1107.             if ($belt.id == supply.id) then
  1108.                 local supply_count = $belt.count
  1109.  
  1110.                 if (supply_count < supply.current_amount) then
  1111.                     supply.current_amount, supply.amount = supply_count, supply.amount + 1
  1112.                 elseif (supply.current_amount ~= supply_count) then
  1113.                     supply.current_amount = supply_count
  1114.                 end
  1115.             end
  1116.         elseif (supply.type == 'DISTANCE_WEAPONS') then
  1117.             if ($rhand.id == supply.id) then
  1118.                 local supply_count = $rhand.count
  1119.  
  1120.                 if (supply_count < supply.current_amount) then
  1121.                     supply.current_amount, supply.amount = supply_count, supply.amount + 1
  1122.                 elseif (supply.current_amount ~= supply_count) then
  1123.                     supply.current_amount = supply_count
  1124.                 end
  1125.             end
  1126.         end
  1127.     end
  1128.  
  1129.     foreach newmessage m do
  1130.         if (m.type == MSG_INFO and m.content:match('^Loot of')) then
  1131.             local loot_info = Untils:parseLootMessage(m.content, true)
  1132.  
  1133.             if (#loot_info.name ~= 0) then
  1134.                 local monster_found = table.binaryfind(self.monsters_killed, loot_info.name:lower(), 'name')
  1135.  
  1136.                 if (monster_found) then
  1137.                     self.monsters_killed[monster_found].amount = self.monsters_killed[monster_found].amount + 1
  1138.                 else
  1139.                     table.binaryinsert(self.monsters_killed, {name = loot_info.name:lower(), amount = 1}, 'name')
  1140.                 end
  1141.  
  1142.                 if (#loot_info.items ~= 0) then
  1143.                     for _, item in ipairs(loot_info.items) do
  1144.                         local item_found = table.binaryfind(self.items_looted, item.name, 'name')
  1145.  
  1146.                         if (item_found) then
  1147.                             self.items_looted[item_found].amount = self.items_looted[item_found].amount + item.amount
  1148.                         else
  1149.                             table.binaryinsert(self.items_looted, {name = item.name:lower(), amount = item.amount, price = math.positive(itemvalue(item.name))}, 'name')
  1150.                         end
  1151.                     end
  1152.                 end
  1153.             end
  1154.         elseif (m.type == MSG_STATUSLOG) then
  1155.             if (string.find(m.content, 'lose')) then
  1156.                 local damage_info = Untils:parseAttackMessage(m.content)
  1157.  
  1158.                 if (#damage_info.dealer.name ~= 0 and #damage_info.target.name ~= 0) then
  1159.                     if (damage_info.dealer.name:lower() == $name:lower()) then
  1160.                         self.damage_dealt = damage_info.damage
  1161.                     end
  1162.  
  1163.                     if (damage_info.target.name:lower() == $name:lower()) then
  1164.                         self.damage_received = damage_info.damage
  1165.                     end
  1166.  
  1167.                     local dealer_found = table.binaryfind(self.damage_stats, damage_info.dealer.name:lower(), 'name')
  1168.  
  1169.                     if (dealer_found) then
  1170.                         self.damage_stats[dealer_found].dealt = self.damage_stats[dealer_found].dealt + damage_info.damage
  1171.                     else
  1172.                         table.binaryinsert(self.damage_stats, {name = damage_info.dealer.name:lower(), dealt = damage_info.damage, received = 0}, 'name')
  1173.                     end
  1174.  
  1175.                     local target_found = table.binaryfind(self.damage_stats, damage_info.target.name:lower(), 'name')
  1176.  
  1177.                     if (target_found) then
  1178.                         self.damage_stats[target_found].received = self.damage_stats[target_found].received + damage_info.damage
  1179.                     else
  1180.                         table.binaryinsert(self.damage_stats, {name = damage_info.target.name:lower(), dealt = 0, received = damage_info.damage}, 'name')
  1181.                     end
  1182.                 end
  1183.             elseif (string.find(m.content, 'heal')) then
  1184.                 local heal_info = Untils:parseHealMessage(m.content)
  1185.  
  1186.                 if (#heal_info.healer ~= 0 and #heal_info.target ~= 0) then
  1187.                     local healer_found = table.binaryfind(self.heal_stats, heal_info.healer:lower(), 'name')
  1188.  
  1189.                     if (healer_found) then
  1190.                         self.heal_stats[healer_found].given = self.heal_stats[healer_found].given + heal_info.damage
  1191.                     else
  1192.                         table.binaryinsert(self.heal_stats, {name = heal_info.healer:lower(), given = heal_info.damage, received = 0}, 'name')
  1193.                     end
  1194.  
  1195.                     local target_found = table.binaryfind(self.heal_stats, heal_info.target:lower(), 'name')
  1196.  
  1197.                     if (target_found) then
  1198.                         self.heal_stats[target_found].received = self.heal_stats[target_found].received + heal_info.damage
  1199.                     else
  1200.                         table.binaryinsert(self.heal_stats, {name = heal_info.target:lower(), given = 0, received = heal_info.damage}, 'name')
  1201.                     end
  1202.                 end
  1203.             end
  1204.         end
  1205.     end
  1206.  
  1207.     foreach creature c 's' do
  1208.         if (Unit:isPlayer(c) and not table.binaryfind(self.players_seen, c.name) and c ~= $self) then
  1209.             table.binaryinsert(self.players_seen, c.name)
  1210.         elseif (not Unit:isNPC(c) and not table.binaryfind(self.monsters_seen, c.id)) then
  1211.             table.binaryinsert(self.monsters_seen, c.id)
  1212.         end
  1213.     end
  1214.    
  1215.     STATS_DATA_RUN_LAST = $timems
  1216. end
  1217.  
  1218. function Stats:clearStatsData(section_name) -- Working
  1219.     if (table.find({SC_ALL_SECTIONS, SC_MONSTERS_SEEN, SC_PLAYERS_SEEN, SC_MONSTERS_KILLED, SC_ITEMS_LOOTED, SC_SUPPLIES_USED, SC_DAMAGE_DEALT, SC_DAMAGE_RECEIVED, SC_DAMAGE_STATS, SC_HEAL_STATS}, section_name)) then
  1220.         for _, section in ipairs({'monsters_seen', 'players_seen', 'monsters_killed', 'items_looted', 'supplies_used', 'damage_dealt', 'damage_received', 'damage_stats', 'heal_stats'}) do
  1221.             if (section_name == SC_ALL_SECTIONS or section_name == exec('return SC_' .. section:upper())) then
  1222.                 if (section == 'damage_dealt' or section == 'damage_received') then
  1223.                     exec('Stats.' .. section .. ' = 0')
  1224.                 else
  1225.                     exec('Stats.' .. section .. ' = {}')
  1226.                 end
  1227.             end
  1228.         end
  1229.  
  1230.         return true
  1231.     end
  1232.  
  1233.     return false
  1234. end
  1235.  
  1236. function Stats:getMonstersSeen() -- Working
  1237.     return #self.monsters_seen
  1238. end
  1239.  
  1240. function Stats:getPlayersSeen(return_names) -- Working
  1241.     if (type(return_names) == 'boolean' and return_names) then
  1242.         return self.players_seen
  1243.     end
  1244.  
  1245.     return #self.players_seen
  1246. end
  1247.  
  1248. function Stats:getMonstersKilled(monster_name) -- Working
  1249.     if (type(monster_name) == 'string') then
  1250.         local monster_found = table.binaryfind(self.monsters_killed, monster_name:lower(), 'name')
  1251.  
  1252.         if (monster_found) then
  1253.             return self.monsters_killed[monster_found].amount
  1254.         end
  1255.  
  1256.         return 0
  1257.     end
  1258.  
  1259.     return self.monsters_killed
  1260. end
  1261.  
  1262. function Stats:addItemsLooted(item_name, item_amount, item_price) -- Working
  1263.     arguments('Stats:addItemsLooted', {'string', item_name, 'number', item_amount})
  1264.  
  1265.     if (#itemname(itemid(item_name)) == 0) then return end
  1266.  
  1267.     local item_found = table.binaryfind(self.items_looted, item_name:lower(), 'name')
  1268.  
  1269.     if (item_found) then
  1270.         self.items_looted[item_found].amount = self.items_looted[item_found].amount + math.positive(item_amount)
  1271.         if (type(item_price) == 'number') then self.items_looted[item_found].price = math.positive(item_price) end
  1272.     else
  1273.         if (type(item_price) ~= 'number') then item_price = itemvalue(item_name) end
  1274.         table.binaryinsert(self.items_looted, {name = item_name:lower(), amount = math.positive(item_amount), price = math.positive(item_price)}, 'name')
  1275.     end
  1276.  
  1277.     return true
  1278. end
  1279.  
  1280. function Stats:getItemsLooted(item_name) -- Working
  1281.     if (type(item_name) == 'string') then
  1282.         local item_found = table.binaryfind(self.items_looted, item_name:lower(), 'name')
  1283.  
  1284.         if (item_found) then
  1285.             return self.items_looted[item_found].amount
  1286.         end
  1287.  
  1288.         return 0
  1289.     end
  1290.  
  1291.     return self.items_looted
  1292. end
  1293.  
  1294. function Stats:addSuppliesUsed(supply_name, supply_amount, supply_price) -- Working
  1295.     arguments('Stats:addSuppliesUsed', {'string', supply_name, 'number', supply_amount})
  1296.  
  1297.     if (#itemname(itemid(supply_name)) == 0) then return end
  1298.  
  1299.     local supply_found = table.binaryfind(self.supplies_used, supply_name:lower(), 'name')
  1300.  
  1301.     if (supply_found) then
  1302.         self.supplies_used[supply_found].amount = self.supplies_used[supply_found].amount + math.positive(supply_amount)
  1303.         if (type(supply_price) == 'number') then self.supplies_used[supply_found].price = math.positive(supply_price) end
  1304.     else
  1305.         if (type(supply_price) ~= 'number') then supply_price = itemcost(supply_name) end
  1306.         table.binaryinsert(self.supplies_used, {name = supply_name:lower(), id = itemid(supply_name), type = 'OTHER', current_amount = 0, amount = math.positive(supply_amount), price = math.positive(supply_price)}, 'name')
  1307.     end
  1308.  
  1309.     return true
  1310. end
  1311.  
  1312. function Stats:getSuppliesUsed(supply_name) -- Working
  1313.     if (type(supply_name) == 'string') then
  1314.         local supply_found = table.binaryfind(self.supplies_used, supply_name:lower(), 'name')
  1315.  
  1316.         if (supply_found) then
  1317.             return self.supplies_used[supply_found].amount
  1318.         end
  1319.  
  1320.         return 0
  1321.     end
  1322.  
  1323.     return self.supplies_used
  1324. end
  1325.  
  1326. function Stats:lastDamageDealt() -- Working
  1327.     return self.damage_dealt
  1328. end
  1329.  
  1330. function Stats:lastDamageReceived() -- Working
  1331.     return self.damage_received
  1332. end
  1333.  
  1334. function Stats:getDamageDealt(creature_name) -- Working
  1335.     arguments('Stats:getDamageDealt', {'string', creature_name})
  1336.  
  1337.     local creature_found = table.binaryfind(self.damage_stats, creature_name:lower(), 'name')
  1338.  
  1339.     if (creature_found) then
  1340.         return self.damage_stats[creature_found].dealt
  1341.     end
  1342.  
  1343.     return 0
  1344. end
  1345.  
  1346. function Stats:getDamageReceived(creature_name) -- Working
  1347.     arguments('Stats:getDamageReceived', {'string', creature_name})
  1348.  
  1349.     local creature_found = table.binaryfind(self.damage_stats, creature_name:lower(), 'name')
  1350.  
  1351.     if (creature_found) then
  1352.         return self.damage_stats[creature_found].received
  1353.     end
  1354.  
  1355.     return 0
  1356. end
  1357.  
  1358. function Stats:getHealGiven(creature_name) -- Working
  1359.     arguments('Stats:getHealGiven', {'string', creature_name})
  1360.  
  1361.     local creature_found = table.binaryfind(self.heal_stats, creature_name:lower(), 'name')
  1362.  
  1363.     if (creature_found) then
  1364.         return self.heal_stats[creature_found].given
  1365.     end
  1366.  
  1367.     return 0
  1368. end
  1369.  
  1370. function Stats:getHealReceived(creature_name) -- Working
  1371.     arguments('Stats:getHealReceived', {'string', creature_name})
  1372.  
  1373.     local creature_found = table.binaryfind(self.heal_stats, creature_name:lower(), 'name')
  1374.  
  1375.     if (creature_found) then
  1376.         return self.heal_stats[creature_found].received
  1377.     end
  1378.  
  1379.     return 0
  1380. end
  1381.  
  1382. local skin_temp = _G['skin']
  1383. _G['skin'] = function(...) -- Working
  1384.     local skin_items, skin_items_before, skin_items_after = {'minotaur leather', 'lizard leather', 'green dragon leather', 'red dragon leather', 'hardened bone', 'perfect behemoth fang'}, {['minotaur leather'] = 0, ['lizard leather'] = 0, ['green dragon leather'] = 0, ['red dragon leather'] = 0, ['hardened bone'] = 0, ['perfect behemoth fang'] = 0}, {['minotaur leather'] = 0, ['lizard leather'] = 0, ['green dragon leather'] = 0, ['red dragon leather'] = 0, ['hardened bone'] = 0, ['perfect behemoth fang'] = 0}
  1385.    
  1386.     for item_name, _ in pairs(skin_items_before) do
  1387.         skin_items_before[item_name] = itemcount(item_name, 'backpack')
  1388.     end
  1389.  
  1390.     wait(200) skin_temp(...) wait(200)
  1391.    
  1392.     for item_name, _ in pairs(skin_items_after) do
  1393.         skin_items_after[item_name] = itemcount(item_name, 'backpack')
  1394.     end
  1395.  
  1396.     for _, item_name in ipairs(skin_items) do
  1397.         if (skin_items_before[item_name] ~= skin_items_after[item_name]) then
  1398.             Stats:addItemsLooted(item_name, 1)
  1399.         end
  1400.     end
  1401. end
  1402.  
  1403. local stake_temp = _G['stake']
  1404. _G['stake'] = function(...) -- Working
  1405.     local stake_items, stake_items_before, stake_items_after = {'vampire dust', 'demon dust'}, {['vampire dust'] = 0, ['demon dust'] = 0}, {['vampire dust'] = 0, ['demon dust'] = 0}
  1406.    
  1407.     for item_name, _ in pairs(stake_items_before) do
  1408.         stake_items_before[item_name] = itemcount(item_name, 'backpack')
  1409.     end
  1410.  
  1411.     wait(200) stake_temp(...) wait(200)
  1412.    
  1413.     for item_name, _ in pairs(stake_items_after) do
  1414.         stake_items_after[item_name] = itemcount(item_name, 'backpack')
  1415.     end
  1416.  
  1417.     for _, item_name in ipairs(stake_items) do
  1418.         if (stake_items_before[item_name] ~= stake_items_after[item_name]) then
  1419.             Stats:addItemsLooted(item_name, 1)
  1420.         end
  1421.     end
  1422. end
  1423.  
  1424. local fish_temp = _G['fish']
  1425. _G['fish'] = function(...) -- Working
  1426.     local fish_items, fish_items_before, fish_items_after = {'giant shimmering pearl (gold)', 'giant shimmering pearl (blue)', 'white pearl', 'small sapphire', "leviathan's amulet"}, {['giant shimmering pearl (gold)'] = 0, ['giant shimmering pearl (blue)'] = 0, ['white pearl'] = 0, ['small sapphire'] = 0, ["leviathan's amulet"] = 0}, {['giant shimmering pearl (gold)'] = 0, ['giant shimmering pearl (blue)'] = 0, ['white pearl'] = 0, ['small sapphire'] = 0, ["leviathan's amulet"] = 0}
  1427.    
  1428.     for item_name, _ in pairs(fish_items_before) do
  1429.         fish_items_before[item_name] = itemcount(item_name, 'backpack')
  1430.     end
  1431.    
  1432.     wait(200) fish_temp(...) wait(200)
  1433.    
  1434.     for item_name, _ in pairs(fish_items_after) do
  1435.         fish_items_after[item_name] = itemcount(item_name, 'backpack')
  1436.     end
  1437.  
  1438.     for _, item_name in ipairs(fish_items) do
  1439.         if (fish_items_before[item_name] ~= fish_items_after[item_name]) then
  1440.             Stats:addItemsLooted(item_name, 1)
  1441.         end
  1442.     end
  1443. end
  1444.  
  1445. function unrust(ignore_common, drop_items) -- Working
  1446.     local rusty_items, unrusted_items, unrusted_items_before, unrusted_items_after = (not ignore_common and {8894, 8895, 8896, 8897, 8898, 8899}) or {8895, 8896, 8898, 8899}, {'brass armor', 'chain armor', 'crown armor', 'golden armor', 'knight armor', 'paladin armor', 'plate armor', 'scale armor', 'brass legs', 'chain legs', 'crown legs', 'golden legs', 'knight legs', 'plate legs', 'studded legs'}, {['brass armor'] = 0, ['chain armor'] = 0, ['crown armor'] = 0, ['golden armor'] = 0, ['knight armor'] = 0, ['paladin armor'] = 0, ['plate armor'] = 0, ['scale armor'] = 0, ['brass legs'] = 0, ['chain legs'] = 0, ['crown legs'] = 0, ['golden legs'] = 0, ['knight legs'] = 0, ['plate legs'] = 0, ['studded legs'] = 0}, {['brass armor'] = 0, ['chain armor'] = 0, ['crown armor'] = 0, ['golden armor'] = 0, ['knight armor'] = 0, ['paladin armor'] = 0, ['plate armor'] = 0, ['scale armor'] = 0, ['brass legs'] = 0, ['chain legs'] = 0, ['crown legs'] = 0, ['golden legs'] = 0, ['knight legs'] = 0, ['plate legs'] = 0, ['studded legs'] = 0}
  1447.    
  1448.     for item_name, _ in pairs(unrusted_items_before) do
  1449.         unrusted_items_before[item_name] = itemcount(item_name, 'backpack')
  1450.     end
  1451.    
  1452.     wait(200)
  1453.  
  1454.     for _, rusty_item in ipairs(rusty_items) do
  1455.         if (itemcount(rusty_item, 'backpack') ~= 0 and itemcount(9016, 'backpack') ~= 0) then
  1456.             useitemon(9016, rusty_item, 'backpack')
  1457.             Stats:addSuppliesUsed('rust remover', 1, 50)
  1458.            
  1459.             break
  1460.         end
  1461.     end
  1462.    
  1463.     wait(200)
  1464.    
  1465.     for item_name, _ in pairs(unrusted_items_after) do
  1466.         unrusted_items_after[item_name] = itemcount(item_name, 'backpack')
  1467.     end
  1468.  
  1469.     if (drop_items) then
  1470.         for _, item_name in ipairs({'brass armor', 'chain armor', 'plate armor', 'scale armor', 'brass legs', 'chain legs', 'plate legs', 'studded legs'}) do
  1471.             if (itemcount(item_name, 'backpack') ~= 0) then
  1472.                 moveitems(item_name, 'ground', 'backpack') waitping()
  1473.             end
  1474.         end
  1475.     end
  1476.  
  1477.     for _, item_name in ipairs(unrusted_items) do
  1478.         if (unrusted_items_before[item_name] ~= unrusted_items_after[item_name]) then
  1479.             Stats:addItemsLooted(item_name, 1)
  1480.         end
  1481.     end
  1482. end
  1483.  
  1484. Targeting = {
  1485.     monster_counts = {['Any'] = '0', ['1'] = '1', ['2+'] = '2', ['2'] = '3', ['3+'] = '4', ['3'] = '5', ['4+'] = '6', ['4'] = '7', ['5+'] = '8', ['5'] = '9', ['6+'] = '10', ['6'] = '11', ['7+'] = '12', ['7'] = '13', ['8+'] = '14', ['8'] = '15', ['9+'] = '16', ['9'] = '17'},
  1486.     monster_attacks = {['no avoidance'] = 'No Avoidance', ['avoid wave'] = 'Avoid Wave', ['avoid beam'] = 'Avoid Beam'},
  1487.     desired_stances = {['no movement'] = 'No Movement', ['strike'] = 'Strike', ['parry'] = 'Parry', ['approach'] = 'Approach', ['circle'] = 'Circle', ['reach'] = 'Reach', ['reach & strike'] = 'Reach & Strike', ['reach & parry'] = 'Reach & Parry', ['reach & circle'] = 'Reach & Circle', ['lure & stand'] = 'Lure & Stand', ['lure & circle'] = 'Lure & Circle', ['keep away'] = 'Keep Away', ['wait & keep away'] = 'Wait & Keep Away', ['away in line'] = 'Away in Line', ['wait & away in line'] = 'Wait & Away in Line', ['lure & keep away'] = 'Lure & Keep Away', ['wait & lure & keep away'] = 'Wait & Lure & Keep Away', ['lose target'] = 'Lose Target'},
  1488.     custom_distances = {['default'] = 'Default', ['2'] = '2', ['3'] = '3', ['4'] = '4', ['5'] = '5', ['6'] = '6', ['7'] = '7', ['8'] = '8', ['9'] = '9'},
  1489.     desired_attacks = {['no action'] = 'No Action', ['attack'] = 'Attack', ['follow'] = 'Follow'},
  1490.     attack_modes = {['no change'] = 'No Change', ['stand/offensive'] = 'Stand/Offensive', ['stand/balanced'] = 'Stand/Balanced', ['stand/defensive'] = 'Stand/Defensive', ['chase/offensive'] = 'Chase/Offensive', ['chase/balanced'] = 'Chase/Balanced', ['chase/defensive'] = 'Chase/Defensive'},
  1491.     event_types = {['normal event'] = 'Normal Event', ['urgent event'] = 'Urgent Event'}
  1492. }
  1493.  
  1494. Targeting.settings = {
  1495.     ['Monsters'] = {['Name'] = function(value) return value end, ['Categories'] = function(value) return value end, ['Count'] = function(value) return (Targeting.monster_counts[tostring(value)] and value) or ('Any') end, ['Setting1'] = {['HpRange'] = function(value) return value or ('0 to 100') end, ['Danger'] = function(value) return math.max(tonumber(value), 0) end, ['MonsterAttacks'] = function(value) return Targeting.monster_attacks[tostring(value):lower()] or ('No Avoidance') end, ['DesiredStance'] = function(value) return Targeting.desired_stances[tostring(value):lower()] or ('No Movement') end, ['CustomDistance'] = function(value) return Targeting.custom_distances[tostring(value):lower()] or ('Default') end, ['DesiredAttack'] = function(value) return Targeting.desired_attacks[tostring(value):lower()] or ('No Action') end, ['FirstSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['SecondSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['ThirdSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['FourthSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['SpellRate'] = function(value) return value or ('2000 to 3000') end, ['SyncSpell'] = function(value) return toyesno(value) end, ['AttackMode'] = function(value) return Targeting.attack_modes[tostring(value):lower()] or ('No Change') end}, ['Setting2'] = {['HpRange'] = function(value) return value or ('0 to 100') end, ['Danger'] = function(value) return math.max(tonumber(value), 0) end, ['MonsterAttacks'] = function(value) return Targeting.monster_attacks[tostring(value):lower()] or ('No Avoidance') end, ['DesiredStance'] = function(value) return Targeting.desired_stances[tostring(value):lower()] or ('No Movement') end, ['CustomDistance'] = function(value) return Targeting.custom_distances[tostring(value):lower()] or ('Default') end, ['DesiredAttack'] = function(value) return Targeting.desired_attacks[tostring(value):lower()] or ('No Action') end, ['FirstSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['SecondSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['ThirdSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['FourthSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['SpellRate'] = function(value) return value or ('2000 to 3000') end, ['SyncSpell'] = function(value) return toyesno(value) end, ['AttackMode'] = function(value) return Targeting.attack_modes[tostring(value):lower()] or ('No Change') end}, ['Setting3'] = {['HpRange'] = function(value) return value or ('0 to 100') end, ['Danger'] = function(value) return math.max(tonumber(value), 0) end, ['MonsterAttacks'] = function(value) return Targeting.monster_attacks[tostring(value):lower()] or ('No Avoidance') end, ['DesiredStance'] = function(value) return Targeting.desired_stances[tostring(value):lower()] or ('No Movement') end, ['CustomDistance'] = function(value) return Targeting.custom_distances[tostring(value):lower()] or ('Default') end, ['DesiredAttack'] = function(value) return Targeting.desired_attacks[tostring(value):lower()] or ('No Action') end, ['FirstSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['SecondSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['ThirdSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['FourthSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['SpellRate'] = function(value) return value or ('2000 to 3000') end, ['SyncSpell'] = function(value) return toyesno(value) end, ['AttackMode'] = function(value) return Targeting.attack_modes[tostring(value):lower()] or ('No Change') end}, ['Setting4'] = {['HpRange'] = function(value) return value or ('0 to 100') end, ['Danger'] = function(value) return math.max(tonumber(value), 0) end, ['MonsterAttacks'] = function(value) return Targeting.monster_attacks[tostring(value):lower()] or ('No Avoidance') end, ['DesiredStance'] = function(value) return Targeting.desired_stances[tostring(value):lower()] or ('No Movement') end, ['CustomDistance'] = function(value) return Targeting.custom_distances[tostring(value):lower()] or ('Default') end, ['DesiredAttack'] = function(value) return Targeting.desired_attacks[tostring(value):lower()] or ('No Action') end, ['FirstSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['SecondSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['ThirdSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['FourthSpell'] = function(value) return string.capitalizeall((Spell:getInfo(tostring(value)) ~= nil and Spell:getInfo(tostring(value)).name) or ('No Action')) end, ['SpellRate'] = function(value) return value or ('2000 to 3000') end, ['SyncSpell'] = function(value) return toyesno(value) end, ['AttackMode'] = function(value) return Targeting.attack_modes[tostring(value):lower()] or ('No Change') end}, ['LootMonster'] = function(value) return toyesno(value) end, ['MustAttackMe'] = function(value) return toyesno(value) end, ['OnlyIfTrapped'] = function(value) return toyesno(value) end, ['PlayAlarm'] = function(value) return toyesno(value) end},
  1496.     ['StanceOptions'] = {['DiagonalMovement'] = function(value) return toyesno(value) or ('no') end, ['RangeDistance'] = function(value) return ((tonumber(value) >= 2 and tonumber(value) <= 9) and value) or ('2') end, ['LureIntensity'] = function(value) return ((tonumber(value) >= 0 and tonumber(value) <= 100) and value) or ('30') end},
  1497.     ['TargetSelection'] = {['ListOrder'] = function(value) return (tonumber(value) > 0 and value) or ('0') end, ['Health'] = function(value) return (tonumber(value) > 0 and value) or ('30') end, ['Proximity'] = function(value) return (tonumber(value) > 0 and value) or ('30') end, ['Danger'] = function(value) return (tonumber(value) > 0 and value) or ('10') end, ['Random'] = function(value) return (tonumber(value) > 0 and value) or ('0') end, ['Stick'] = function(value) return (tonumber(value) > 0 and value) or ('2') end, ['MustBeReachable'] = function(value) return toyesno(value) or ('yes') end, ['MustBeShootable'] = function(value) return toyesno(value) or ('no') end},
  1498.     ['TargetingPriority'] = {['Priority'] = function(value) return (tonumber(value) > 0 and value) or ('60') end, ['OverridePriority'] = function(value) return (tonumber(value) > 0 and value) or ('0') end, ['ExpireTime'] = function(value) return (tonumber(value) > 0 and value) or ('2000') end, ['LifeTime'] = function(value) return (tonumber(value) > 0 and value) or ('5000') end, ['EventType'] = function(value) return Targeting.event_types[tostring(value):lower()] or ('Normal Event') end},
  1499.     ['TargetingEnabled'] = function(value) return toyesno(value) end
  1500. }
  1501.  
  1502. function Targeting:monsters(monster_name, monster_count)
  1503.     local monster = {
  1504.         name = monster_name,
  1505.         count = monster_count
  1506.     }
  1507.  
  1508.     function monster:set(setting_path, value, update_gui)
  1509.         arguments('Targeting:monsters():set', {'string', setting_path})
  1510.        
  1511.         if (type(update_gui) ~= 'boolean') then update_gui = true end
  1512.         local setting_path = Targeting:getPath(self.name .. '_' .. Targeting.monster_counts[self.count] .. '/' .. setting_path)
  1513.        
  1514.         if (setting_path) then
  1515.             local setting_path_parts = setting_path:token(nil, '/')
  1516.            
  1517.             if (setting_path_parts[2] == 'Monsters') then
  1518.                 if (not string.find(setting_path_parts[4], 'Setting')) then
  1519.                     setsetting(setting_path, tostring(Targeting.settings[setting_path_parts[2]][setting_path_parts[4]](value)), update_gui)
  1520.                     if (setting_path_parts[4] == 'Name') then self.name = value elseif (setting_path_parts[4] == 'Count') then self.count = value end
  1521.                 else
  1522.                     setsetting(setting_path, tostring(Targeting.settings[setting_path_parts[2]][setting_path_parts[4]][setting_path_parts[5]](value)), update_gui)
  1523.                 end
  1524.             end
  1525.         end
  1526.  
  1527.         return self
  1528.     end
  1529.  
  1530.     function monster:get(setting_path)
  1531.         arguments('Targeting:monsters():get', {'string', setting_path})
  1532.  
  1533.         return getsetting(Targeting:getPath(self.name .. '_' .. Targeting.monster_counts[self.count] .. '/' .. setting_path))
  1534.     end
  1535.  
  1536.     return monster
  1537. end
  1538.  
  1539. function Targeting:set(setting_path, value, update_gui) -- Working
  1540.     arguments('Targeting:set', {'string', setting_path})
  1541.  
  1542.     if (type(update_gui) ~= 'boolean') then update_gui = true end
  1543.     local setting_path = Targeting:getPath(setting_path)
  1544.    
  1545.     if (setting_path) then
  1546.         local setting_path_parts = setting_path:token(nil, '/')
  1547.        
  1548.         if (setting_path_parts[2] == 'TargetingEnabled') then
  1549.             setsetting(setting_path, tostring(Targeting.settings[setting_path_parts[2]](value)), update_gui)
  1550.         elseif (setting_path_parts[2] ~= 'Monsters') then
  1551.             setsetting(setting_path, tostring(Targeting.settings[setting_path_parts[2]][setting_path_parts[3]](value)), update_gui)
  1552.         else
  1553.             if (not string.find(setting_path_parts[4], 'Setting')) then
  1554.                 setsetting(setting_path, tostring(Targeting.settings[setting_path_parts[2]][setting_path_parts[4]](value)), update_gui)
  1555.             else
  1556.                 setsetting(setting_path, tostring(Targeting.settings[setting_path_parts[2]][setting_path_parts[4]][setting_path_parts[5]](value)), update_gui)
  1557.             end
  1558.         end
  1559.     end
  1560.  
  1561.     return self
  1562. end
  1563.  
  1564. function Targeting:getPath(setting_path) -- Working
  1565.     arguments('Targeting:getPatch', {'string', setting_path})
  1566.    
  1567.     local setting_path = setting_path:gsub('^Targeting/', '')
  1568.     local setting_path_extended = 'Targeting/' .. setting_path
  1569.    
  1570.     if (getsetting(setting_path_extended) ~= nil) then
  1571.         return setting_path_extended
  1572.     else
  1573.         for _, section in ipairs({'Monsters', 'StanceOptions', 'TargetSelection', 'TargetingPriority', 'TargetingEnabled'}) do
  1574.             setting_path_extended = 'Targeting/' .. section .. '/' .. setting_path
  1575.            
  1576.             if (getsetting(setting_path_extended) ~= nil) then
  1577.                 return setting_path_extended
  1578.             end
  1579.         end
  1580.     end
  1581.  
  1582.     return nil
  1583. end
  1584.  
  1585. function Targeting:get(setting_path) -- Working
  1586.     arguments('Targeting:get', {'string', setting_path})
  1587.  
  1588.     return getsetting(Targeting:getPath(setting_path))
  1589. end
  1590.  
  1591. function Targeting:setState(value, stop_attack, update_gui) -- Working
  1592.     if (type(stop_attack) ~= 'boolean') then stop_attack = false end
  1593.     if (type(update_gui) ~= 'boolean') then update_gui = true end
  1594.  
  1595.     setsetting('Targeting/TargetingEnabled', toyesno(value), update_gui)
  1596.     if (toyesno(value) and stop_attack) then stopattack() end
  1597.  
  1598.     return self
  1599. end
  1600.  
  1601. function Targeting:getState() -- Working
  1602.     return getsetting('Targeting/TargetingEnabled')
  1603. end
  1604.  
  1605.  
  1606. ------------------------------LucasTerraDefaultSettings.lua---------------------------------
  1607.  
  1608.  
  1609.  
  1610. LUCASSETTINGS_LIB = '1.2'
  1611. print('Lucas Terra Default Settings Version: '..LUCASSETTINGS_LIB)
  1612. local changesettings = true
  1613. if changesettings then
  1614.     --setsetting('Cavebot/Looting/MoveItemsQuickly', 'yes') -- Enable it if you like, just remove the '--' in the beginning
  1615.     setsetting('Cavebot/Pathfinding/WalkableIds', '140\n404\n831-834\n883\n2131-2135\n2314-2316\n2319\n2346-2385\n2418-2426\n2431-2434\n2441-2444\n2469\n2471-2473\n2478\n2480-2486\n2519\n2523\n2775-2812\n2981-2985\n2987-2988\n3503-3504\n3514\n3807\n5086-5088\n6114-6115\n6355-6362\n6371-6372\n7864\n8455\n8763\n9061-9062\n10207\n10209\n10216\n10286\n10287-10288\n11009')
  1616.     setsetting('Hud/DisplaysList/ActiveHotkeys/Enabled', 'yes')
  1617.     setsetting('Hud/HudPolicy', 'Show if focused')
  1618.     setsetting('Input/Keyboard/KeyboardMode', 'Simulate keyboard')
  1619.     setsetting('Input/Keyboard/StuckCtrlShiftPolicy', 'If cavebot on, release after 1 sec')
  1620.     setsetting('Input/Keyboard/TypeWaitTime', '20 to 45')
  1621.     setsetting('Input/Keyboard/PressWaitTime', '45 to 65')
  1622.     setsetting('Input/Mouse/MouseMode', 'Simulate mouse') --'Control mouse /permit'
  1623.     setsetting('Input/Mouse/ScrollMode', 'Use mouse wheel')
  1624.     setsetting('Input/Mouse/StuckCursorPolicy', 'If cavebot on, release instantly')
  1625.     setsetting('Input/Mouse/MoveSpeed', 'Instantaneous') --Instantaneous
  1626.     setsetting('Input/Mouse/ClickWaitTime', '20 to 35')
  1627.     setsetting('Input/OpenMenuPolicy', 'Confirm if cavebotting')
  1628.     setsetting('Hotkeys/HotkeyCondition', 'Client focus required')
  1629.     if not getsetting('Hotkeys/HotkeyList/HideUnhideBot/Script') then
  1630.         addhotkey("HideUnhideBot", "listas('dontlist')\nshowbot()\nwait(300)", "u", "ctrl")
  1631.     else
  1632.         setsetting('Hotkeys/HotkeyList/HideUnhideBot/Script', "listas('dontlist')\nshowbot()\nwait(300)")
  1633.     end
  1634.     if not getsetting('Hotkeys/HotkeyList/HideUnhideSettings/Script') then
  1635.         addhotkey("HideUnhideSettings", "listas('dontlist')\nshowsettings()\nwait(300)", "j", "ctrl")
  1636.     else
  1637.         setsetting('Hotkeys/HotkeyList/HideUnhideSettings/Script', "listas('dontlist')\nshowsettings()\nwait(300)")
  1638.     end
  1639.     if not getsetting('Hotkeys/HotkeyList/PauseHotkey/Script') then
  1640.         addhotkey("PauseHotkey", "if not $targeting or not $cavebot then\n  settargeting('on')\n    setcavebot('on')\n  setlooting('on')\n  listas('Cavebot Resumed')\nelse\n   settargeting('off')\n   setcavebot('off')\n setlooting('off')\n listas('Cavebot Paused.')\nend\nwait(300)", "pause")
  1641.     end
  1642. end
  1643.  
  1644.  
  1645. ------------------------------LucasTerra.lua---------------------------------
  1646.  
  1647. --12.4, Report bug on Lucas Terra's Library Thread: http://forums.tibianeobot.com/showthread.php?1013
  1648. LUCAS_LIB = '12.4'
  1649. print('Lucas Terra Library Version: '..LUCAS_LIB)
  1650.  
  1651. -- Item Properties
  1652. ITEM_NOTROOFEDGE = 0
  1653. ITEM_TOPORDER1 = 1 --always on top
  1654. ITEM_TOPORDER2 = 2 --walktrough (doors)
  1655. ITEM_TOPORDER3 = 3 --walktrough (arcs)
  1656. ITEM_CONTAINER = 4
  1657. ITEM_STACKABLE = 5
  1658. ITEM_CORPSE = 6
  1659. ITEM_USEABLE = 7
  1660. ITEM_WRITEABLE = 8
  1661. ITEM_READABLE = 9
  1662. ITEM_FLUIDCONTAINER = 10
  1663. ITEM_SPLASH = 11
  1664. ITEM_BLOCKWALK = 12
  1665. ITEM_NOTMOVEABLE = 13
  1666. ITEM_BLOCKSHOTS = 14
  1667. ITEM_BLOCKPATHS = 15
  1668. ITEM_PICKUPABLE = 16
  1669. ITEM_HANGABLE = 17
  1670. ITEM_HORIZONTAL = 18
  1671. ITEM_VERTICAL = 19
  1672. ITEM_ROTATEABLE = 20
  1673. ITEM_LIGHTFONT = 21
  1674. ITEM_UNKNOWN = 22
  1675. ITEM_FLOORCHANGE = 23
  1676. ITEM_OFFSET = 24
  1677. ITEM_HEIGHTED = 25
  1678. ITEM_BIGSPRITE = 26
  1679. ITEM_UNEXIST = 27
  1680. ITEM_MINIMAP = 28
  1681. ITEM_ACTION = 29
  1682. ITEM_GROUND = 30
  1683. ITEM_DIAGONALBORDER,ITEM_BORDER = 31,31
  1684.  
  1685. -- Credits to Anonymickey, for testing the msg types
  1686. MSG_STATUS = 0 -- Status messages (In the screen).
  1687. MSG_DEFAULT = 1 -- Any player/npc message in Default channel.
  1688. MSG_WHISPER = 2 -- Any player whispering.
  1689. MSG_YELL = 3 -- Any player yelling.
  1690. MSG_NPC = 5 -- Any NPC answers in NPC channel.
  1691. MSG_PVT = 6 -- Private messages from other players.
  1692. MSG_CHANNEL = 7 -- Any player message in Game/Help/Real/Tutor/Trade channel.
  1693. MSG_RED = 15 -- Red alert messages.
  1694. MSG_RAID,MSG_ADVANCE = 16,16 -- Any white alert message.
  1695. MSG_WELCOME = 17 -- Game/Channel welcome messages.
  1696. MSG_STATUSLOG = 18 -- Status messages in Server Log.
  1697. MSG_INFO = 19 -- Green messages (like loot message) in Server Log.
  1698. MSG_SENT = 21 -- Private messages sent by you.
  1699.  
  1700. -- Skull Types
  1701. SKULL_NOSKULL = 0
  1702. SKULL_YELLOW = 1
  1703. SKULL_GREEN = 2
  1704. SKULL_WHITE = 3
  1705. SKULL_RED = 4
  1706. SKULL_BLACK = 5
  1707. SKULL_ORANGE = 6
  1708.  
  1709. -- WarBanner Types
  1710. WAR_NOWAR = 0
  1711. WAR_GREEN = 1 --Friend
  1712. WAR_RED = 2 --Enemy
  1713. WAR_BLUE = 3 --In a War that you're not fighting
  1714.  
  1715. -- Party Types
  1716. PARTY_NOPARTY = 0
  1717. PARTY_INVITED_LEADER = 1 -- Leader inviting you to party
  1718. PARTY_INVITED_MEMBER = 2 -- Member invited to party
  1719. PARTY_ONPARTY_MEMBER = 3 -- Member of a party
  1720. PARTY_ONPARTY_LEADER = 4 -- Leader of the party
  1721. PARTY_EXPSHARE_OK_MEMBER = 5 -- Exp Share Working Fine, member of a party
  1722. PARTY_EXPSHARE_OK_LEADER = 6 -- Exp Share Working Fine, leader of the party
  1723. PARTY_EXPSHARE_WAIT_MEMBER = 7 -- Exp Share on standby, member of a party
  1724. PARTY_EXPSHARE_WAIT_LEADER = 8 -- Exp Share on standby, leader of the party
  1725. PARTY_EXPSHARE_OFF_MEMBER = 9 -- Exp Disabled because of a low level char or player in different floor, member of a party
  1726. PARTY_EXPSHARE_OFF_LEADER = 10 -- Exp Disabled because of a low level char or player in different floor, leader of the party
  1727.  
  1728. ASCII = {'', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', '', ' ', '!', '"', '#', '$', '%', '&', "'", '(', ')', '*', '+', ',', '-', '.', '/', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', ':', ';', '<', '=', '>', '?', '@', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', '[', '', ']', '^', '_', '`', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', '{', '|', '}', '~'}
  1729.  
  1730. -- Rune IDs
  1731. RUNE_SD = 3155
  1732. RUNE_UH = 3160
  1733. RUNE_IH = 3152
  1734. RUNE_HMM = 3198
  1735. RUNE_ICICLE = 3158
  1736. RUNE_STALAGMITE = 3179
  1737. RUNE_FIREBALL = 3189
  1738. RUNE_LMM = 3174
  1739. RUNE_HOLY = 3182
  1740. RUNE_MWALL = 3180
  1741. RUNE_GROWTH = 3156
  1742. RUNE_PARALYZE = 3165
  1743. RUNE_GFB = 3191
  1744. RUNE_AVALANCHE = 3161
  1745. RUNE_STONESHOWER = 3175
  1746. RUNE_THUNDERSTORM = 3202
  1747. RUNE_EXPLO = 3200
  1748. RUNE_SOULFIRE = 3195
  1749.  
  1750. SCREEN_LEFT = -8
  1751. SCREEN_TOP = -6
  1752. SCREEN_BOTTOM = 7
  1753. SCREEN_RIGHT = 9
  1754.  
  1755. GLOBAL_BALANCE = 0
  1756. GLOBAL_HUNGRY = 0
  1757.  
  1758. _CREATUREPROPERTIES = {'name', 'id', 'posx', 'posy', 'posz', 'dir', 'outfit', 'color1', 'color2', 'color3', 'color4', 'addons', 'mount', 'lightintensity', 'lightcolor', 'hppc', 'speed', 'updated', 'skull', 'party', 'warbanner', 'dist', 'ignored', 'ismonster', 'isplayer', 'isshootable', 'lastattacked'}
  1759. local shields = {3409, 3410, 3411, 3412, 3413, 3414, 3415, 3416, 3417, 3418, 3419, 3420, 3421, 3422, 3423, 3424, 3425, 3426, 3427, 3428, 3429, 3430, 3431, 3432, 3433, 3434, 3435, 3436, 3437, 3438, 3439, 3440, 3441, 3442, 3443, 3444, 3445, 6131, 6390, 6432, 7460, 8077, 8078, 8079, 8080, 8081, 9372, 9372, 9377, 9380, 9401, 11688}
  1760. local spellbooks = {3059, 8072, 8073, 8074, 8075, 8076, 8090, 11691}
  1761. local axes = {665, 666, 667, 668, 669, 684, 685, 686, 687, 688, 783, 785, 786, 787, 788, 801, 802, 803, 804, 805, 3266, 3268, 3269, 3274, 3275, 3276, 3293, 3302, 3303, 3306, 3313, 3314, 3315, 3316, 3317, 3318, 3319, 3320, 3323, 3328, 3329, 3331, 3335, 3342, 3344, 3346, 6553, 7380, 7388, 7389, 7411, 7412, 7413, 7419, 7420, 7433, 7434, 7435, 7436, 7453, 7454, 7455, 7456, 7773, 8096, 8097, 8098, 9384, 10388, 10406, 11657}
  1762. local clubs = {670, 671, 672, 673, 674, 689, 690, 691, 692, 693, 789, 790, 791, 792, 793, 806, 807, 808, 809, 810, 3208, 3270, 3279, 3282, 3286, 3289, 3304, 3305, 3309, 3310, 3311, 3312, 3321, 3322, 3324, 3325, 3327, 3332, 3333, 3336, 3337, 3340, 3341, 3343, 3348, 3453, 7379, 7381, 7387, 7392, 7409, 7410, 7414, 7415, 7421, 7422, 7423, 7424, 7425, 7426, 7427, 7428, 7429, 7430, 7431, 7432, 7437, 7450, 7451, 7452, 8099, 8100, 8101, 9373, 9385, 10391}
  1763. local swords = {660, 661, 662, 663, 664, 679, 680, 681, 682, 683, 779, 780, 781, 782, 783, 794, 795, 796, 797, 798, 3264, 3265, 3267, 3271, 3272, 3273, 3278, 3280, 3281, 3283, 3284, 3285, 3288, 3290, 3291, 3292, 3294, 3295, 3296, 3297, 3299, 3300, 3301, 3307, 3308, 3326, 3330, 3334, 3338, 3339, 3345, 6101, 6527, 7382, 7383, 7384, 7385, 7386, 7390, 7391, 7402, 7403, 7404, 7405, 7406, 7407, 7408, 7416, 7417, 7418, 7449, 7774, 8102, 8103, 8104, 9375, 9386, 9387, 9396, 10389, 10390, 10392, 11693}
  1764. local distone = {1781, 2992, 3277, 3287, 3298, 3347, 7366, 7367, 7368, 7378}
  1765. local bows = {3349, 3350, 5803, 5907, 7438, 8021, 8022, 8023, 8024, 8025, 8026, 8027, 8028, 8029, 8030, 9378}
  1766. local wands = {3071, 3072, 3073, 3074, 3075, 8092, 8093, 8094}
  1767. local rods = {3065, 3066, 3067, 3069, 3070, 8082, 8083, 8084}
  1768. local ammos = {761, 762, 763, 774, 3446, 3447, 3448, 3449, 3450, 6528, 7363, 7364, 7365}
  1769. local ropes = {646, 3003, 9594, 9596, 9598}
  1770. local shovels = {3457, 5710, 9594, 9596, 9598}
  1771. local machetes = {3308, 3330, 9594, 9596, 9598}
  1772. local picks = {3456, 9594, 9596, 9598}
  1773. local eatfoodids = {3577, 3578, 3579, 3580, 3581, 3582, 3583, 3584, 3585, 3586, 3587, 3588, 3589, 3590, 3591, 3592, 3593, 3594, 3595, 3596, 3597, 3598, 3599, 3600, 3601, 3602, 3606, 3607, 3723, 3724, 3725, 3726, 3727, 3728, 3729, 3730, 3731, 3732, 3910, 3911, 3912, 3913, 3914, 3915, 3916, 3917, 3918, 3919, 3920, 5678, 8010}
  1774. local foods = {{169, 108}, {836, 48}, {841, 48}, {901, 720}, {904, 180}, {3577, 180}, {3578, 144}, {3579, 120}, {3580, 204}, {3581, 48}, {3582, 360}, {3583, 720}, {3584, 60}, {3585, 72}, {3586, 156}, {3587, 96}, {3588, 12}, {3589, 216}, {3590, 12}, {3591, 24}, {3592, 108}, {3593, 240}, {3594, 204}, {3595, 60}, {3596, 72}, {3597, 108}, {3598, 24}, {3599, 24}, {3600, 120}, {3601, 36}, {3602, 96}, {3606, 72}, {3607, 108}, {3723, 108}, {3724, 48}, {3725, 264}, {3726, 360}, {3727, 108}, {3728, 72}, {3729, 144}, {3730, 36}, {3731, 432}, {3732, 60}, {5096, 48}, {5678, 96}, {6125, 96}, {6277, 120}, {6278, 180}, {6392, 144}, {6393, 180}, {6500, 240}, {6541, 72}, {6542, 72}, {6543, 72}, {6544, 72}, {6545, 72}, {6569, 12}, {6574, 60}, {7158, 300}, {7159, 180}, {7372, 24}, {7373, 24}, {7375, 24}, {7377, 24}, {8010, 120}, {8011, 60}, {8012, 12}, {8013, 12}, {8014, 84}, {8015, 60}, {8016, 12}, {8017, 60}, {8019, 132}, {8177, 88}, {8197, 60}, {10219, 120}, {10329, 180}, {10453, 36}, {11459, 240}, {11460, 120}, {11461, 96}, {11462, 108}, {11681, 660}, {11682, 216}, {11683, 24}, {12310, 240}}
  1775. local healthpots = {236, 239, 266, 7642, 7643, 7876}
  1776. local manapots = {237, 238, 268, 7642}
  1777. local rustyequips = {8891, 8892, 8893, 8894, 8895, 8896, 8897, 8898, 8899, 8900, 8901, 8902, 8903, 8904, 8905, 8906, 8907, 8908}
  1778. local closeddoorsids = {1628, 1629, 1631, 1632, 1638, 1640, 1642, 1644, 1646, 1648, 1650, 1651, 1653, 1654, 1656, 1658, 1660, 1662, 1664, 1666, 1668, 1669, 1671, 1672, 1674, 1676, 1678, 1680, 1682, 1683, 1685, 1687, 1689, 1691, 1692, 1694, 1696, 1698, 4912, 4913, 5006, 5007, 5082, 5084, 5097, 5098, 5100, 5102, 5104, 5106, 5107, 5109, 5111, 5113, 5115, 5116, 5118, 5120, 5122, 5124, 5125, 5127, 5129, 5131, 5133, 5134, 5136, 5137, 5139, 5140, 5142, 5143, 5277, 5278, 5280, 5281, 5282, 5285, 5287, 5289, 5291, 5293, 5302, 5303, 5514, 5516, 5745, 5749, 6191, 6192, 6194, 6195, 6197, 6199, 6201, 6203, 6205, 6207, 6248, 6249, 6251, 6252, 6254, 6258, 6260, 6262, 6264, 6435, 6436, 6439, 6440, 6443, 6444, 6449, 6450, 6453, 6454, 6457, 6458, 6461, 6462, 6465, 6466, 6469, 6470, 6788, 6789, 6891, 6892, 6894, 6896, 6898, 6900, 6901, 6903, 6905, 6907, 7027, 7028, 7033, 7034, 7036, 7038, 7040, 7042, 7043, 7045, 7047, 7049, 7051, 7052, 7711, 7712, 7714, 7715, 7717, 7719, 7721, 7723, 7725, 7727, 7868, 7941, 8249, 8250, 8252, 8253, 8255, 8257, 8258, 8261, 8263, 8265, 8351, 8352, 8354, 8355, 8357, 8359, 8361, 8363, 8365, 8367, 9347, 9348, 9351, 9352, 9354, 9355, 9357, 9359, 9361, 9363, 9365, 9367, 9551, 9552, 9554, 9556, 9558, 9560, 9561, 9563, 9565, 9567, 9571, 9572, 9858, 9859, 9863, 9865, 9867, 9868, 9872, 9874, 10147, 10149, 10151, 10153, 10155, 10157, 10520, 10521, 11232, 11233, 11237, 11239, 11241, 11242, 11246, 11248, 11705}
  1779. --                     {1628, 1629, 1631, 1632, 1638, 1640, 1650, 1651, 1653, 1654, 1656, 1658, 1668, 1669, 1671, 1672, 1682, 1683, 1685, 1691, 1692, 1694, 4912, 4913, 5006, 5007, 5082, 5084, 5097, 5098, 5100, 5106, 5107, 5109, 5115, 5116, 5118, 5124, 5125, 5127, 5133, 5134, 5136, 5137, 5139, 5140, 5142, 5143, 5277, 5278, 5280, 5281, 5283, 5285, 5514, 5516, 5732, 5733, 5735, 5736, 6191, 6192, 6194, 6195, 6197, 6199, 6248, 6249, 6251, 6252, 6254, 6256, 6891, 6892, 6894, 6900, 6901, 6903, 7033, 7034, 7036, 7042, 7043, 7045, 7054, 7056, 7711, 7712, 7714, 7715, 7717, 7719, 8249, 8250, 8252, 8253, 8255, 8257, 8351, 8352, 8354, 8355, 8357, 8359, 9351, 9352, 9354, 9355, 9357, 9359, 9551, 9552, 9554, 9560, 9561, 9563, 9858, 9859, 9867, 9868, 11136, 11137, 11143, 11144, 11232, 11233, 11241, 11242, 11705, 11714, 12033, 12035, 12249, 12250}
  1780. local openeddoorsids = {1630, 1633, 1639, 1641, 1643, 1645, 1647, 1649, 1652, 1655, 1657, 1659, 1661, 1663, 1665, 1667, 1670, 1673, 1675, 1677, 1679, 1681, 1684, 1686, 1688, 1690, 1693, 1695, 1697, 1699, 2178, 2180, 4911, 4914, 5083, 5085, 5099, 5101, 5103, 5105, 5108, 5110, 5112, 5114, 5117, 5119, 5121, 5123, 5126, 5128, 5130, 5132, 5135, 5138, 5141, 5144, 5279, 5282, 5284, 5286, 5288, 5290, 5292, 5294, 5515, 5117, 5746, 5748, 6193, 6196, 6198, 6200, 6202, 6204, 6206, 6208, 6250, 6253, 6255, 6257, 6259, 6261, 6263, 6265, 6893, 6895, 6897, 6899, 6902, 6904, 6906, 6908, 7035, 7037, 7039, 7041, 7044, 7046, 7048, 7050, 7713, 7716, 7718, 7720, 7722, 7724, 7726, 7728, 7869, 8251, 8254, 8256, 8258, 8260, 8262, 8264, 8266, 8353, 8356, 8358, 8360, 8362, 8364, 8366, 8368, 9353, 9356, 9358, 9360, 9362, 9364, 9366, 9368, 9553, 9555, 9557, 9559, 9562, 9564, 9566, 9568, 9860, 9864, 9866, 9869, 9873, 9875, 11234, 11238, 11240, 11243, 11247, 11249, 11708}
  1781. --                     {1630, 1633, 1639, 1641, 1652, 1655, 1657, 1659, 1670, 1673, 1684, 1686, 1693, 1695, 4911, 4914, 5083, 5085, 5099, 5101, 5108, 5110, 5117, 5119, 5126, 5128, 5135, 5138, 5141, 5144, 5279, 5282, 5284, 5286, 5515, 5517, 5734, 5737, 6193, 6196, 6198, 6200, 6250, 6253, 6255, 6257, 6893, 6895, 6902, 6904, 7035, 7037, 7044, 7046, 7055, 7057, 7713, 7716, 7718, 7720, 8251, 8254, 8256, 8258, 8353, 8356, 8358, 8360, 9353, 9356, 9358, 9360, 9553, 9555, 9562, 9564, 9860, 9869, 11138, 11145, 11234, 11243, 11708, 11716, 12034, 12036}
  1782. local rashid = {662, 664, 667, 669, 672, 680, 681, 683, 686, 688, 691, 780, 781, 783, 786, 788, 791, 795, 796, 798, 803, 805, 808, 811, 812, 813, 814, 815, 816, 817, 818, 819, 820, 821, 822, 823, 824, 825, 826, 827, 828, 829, 830, 2991, 3002, 3006, 3007, 3008, 3010, 3016, 3017, 3018, 3019, 3025, 3055, 3063, 3290, 3314, 3315, 3326, 3327, 3328, 3330, 3332, 3333, 3334, 3339, 3340, 3342, 3344, 3356, 3360, 3364, 3366, 3386, 3397, 3404, 3408, 3414, 3420, 3421, 3435, 3436, 3440, 3441, 3442, 3550, 3554, 3556, 5461, 5710, 5741, 5810, 5917, 5918, 6095, 6096, 6131, 6299, 6553, 7379, 7381, 7382, 7383, 7384, 7386, 7387, 7388, 7389, 7402, 7403, 7404, 7408, 7414, 7415, 7418, 7419, 7422, 7424, 7425, 7426, 7427, 7430, 7432, 7437, 7449, 7452, 7456, 7457, 7460, 7461, 7462, 7463, 7464, 8022, 8027, 8045, 8049, 8050, 8052, 8061, 8063, 9013, 9014, 9017, 9302, 9304, 11674}
  1783. local greendjinn = {3048, 3051, 3052, 3053, 3054, 3065, 3066, 3067, 3069, 3070, 3078, 3084, 3085, 3097, 3098, 3214, 3281, 3297, 3299, 3307, 3318, 3322, 3324, 3369, 3370, 3371, 3373, 3383, 3384, 3428, 3429, 3432, 3434, 3574, 7407, 7411, 7413, 7419, 7421, 7428, 8082, 8083, 8084}
  1784. local bluedjinn = {674, 679, 693, 779, 793, 794, 810, 3046, 3049, 3050, 3056, 3060, 3061, 3062, 3071, 3072, 3073, 3074, 3075, 3079, 3081, 3082, 3083, 3091, 3092, 3093, 3271, 3279, 3280, 3284, 3301, 3302, 3313, 3320, 3380, 3381, 3382, 3385, 3391, 3392, 3415, 3416, 3418, 3419, 3439, 3567, 7391, 7410, 7412, 7436, 7451, 7454, 8092, 8093, 8094}
  1785. local creatureproducts = {3044, 4839, 5808, 5876, 5877, 5878, 5879, 5881, 5882, 5883, 5890, 5893, 5894, 5895, 5896, 5897, 5898, 5899, 5900, 5901, 5902, 5905, 5906, 5919, 5920, 5925, 5930, 5943, 5948, 5954, 6535, 6540, 6546, 7290, 7786, 7882, 8031, 8143, 9053, 9054, 9055, 9393, 9606, 9631, 9632, 9633, 9634, 9635, 9636, 9637, 9638, 9639, 9640, 9641, 9642, 9643, 9644, 9645, 9646, 9647, 9648, 9649, 9650, 9651, 9652, 9654, 9655, 9656, 9657, 9658, 9659, 9660, 9661, 9662, 9663, 9664, 9665, 9666, 9667, 9668, 9683, 9684, 9685, 9686, 9688, 9689, 9690, 9691, 9692, 9693, 9694, 10196, 10272, 10273, 10274, 10275, 10276, 10277, 10278, 10279, 10280, 10281, 10282, 10283, 10289, 10291, 10292, 10293, 10295, 10296, 10297, 10298, 10299, 10300, 10301, 10302, 10303, 10304, 10305, 10306, 10307, 10308, 10309, 10310, 10311, 10312, 10313, 10314, 10315, 10316, 10317, 10318, 10319, 10320, 10321, 10397, 10404, 10405, 10407, 10408, 10409, 10410, 10411, 10413, 10414, 10415, 10416, 10417, 10418, 10420, 10444, 10449, 10450, 10452, 10454, 10455, 10456, 11443, 11444, 11445, 11446, 11447, 11448, 11449, 11450, 11451, 11452, 11453, 11454, 11455, 11456, 11457, 11458, 11463, 11464, 11465, 11466, 11467, 11469, 11470, 11471, 11472, 11473, 11474, 11475, 11476, 11477, 11478, 11479, 11480, 11481, 11482, 11483, 11484, 11485, 11486, 11487, 11488, 11489, 11490, 11491, 11492, 11493, 11510, 11511, 11512, 11513, 11514, 11515, 11539, 11658, 11659, 11660, 11661, 11666, 11671, 11672, 11673, 11680, 11684, 11702, 11703, 12172, 12312, 12313, 12314, 12601, 12742, 12805}
  1786. --left: cavebear skull, draptor scales, giant crab pincer, maxilla, panther head, panther paw, coal (nuggets), demonic finger, eye of a deepling, flintstone, white deer skin
  1787. local backpackstring = {'brown backpack', 'beach backpack', 'blue backpack', 'brocade backpack', 'camouflage backpack', 'crown backpack', 'demon backpack', 'dragon backpack', 'expedition backpack', 'fur backpack', 'golden backpack', 'green backpack', 'grey backpack', 'heart backpack', 'minotaur backpack', 'moon backpack', 'orange backpack', 'pirate backpack', 'purple backpack', 'red backpack', 'santa backpack', 'yellow backpack', 'backpack of holding', 'jewelled backpack'}
  1788. local backpacks = {2854, 5949, 2869, 8860, 2872, 9605, 9601, 10326, 10324, 7342, 2871, 2865, 2870, 10202, 10327, 9604, 9602, 5926, 2868, 2867, 10346, 2866, 3253, 5801}
  1789.  
  1790. function swap(a,b,c)
  1791.     local t
  1792.     if type(a) == 'table' then
  1793.         t = a[b]
  1794.         a[b]=a[c]
  1795.         a[c]=t
  1796.     else
  1797.         t=a
  1798.         a=b
  1799.         b=t
  1800.     end
  1801. end
  1802.  
  1803. function qs1(tablename, left, right)
  1804.     if type(tablename) == 'table' then
  1805.         left = left or 1
  1806.         right = right or #tablename
  1807.         local i,j,x
  1808.         if right-left+1 <= 25 then
  1809.             for i=left+1, right do
  1810.                 x=tablename[i]
  1811.                 j=i-1
  1812.                 while j>=left and x<tablename[j] do
  1813.                     tablename[j+1]=tablename[j]
  1814.                     j=j-1
  1815.                 end
  1816.                 tablename[j+1]=x
  1817.             end
  1818.         else
  1819.             i,j,x = left, right, tablename[math.floor((left+right)/2)]
  1820.             local temp
  1821.             repeat
  1822.                 while tablename[i]<x and i < right do
  1823.                     i = i+1
  1824.                 end
  1825.                 while tablename[j]>x and j > left do
  1826.                     j = j-1
  1827.                 end
  1828.                 if (i <= j) then
  1829.                     temp = tablename[i]
  1830.                     tablename[i] = tablename[j]
  1831.                     tablename[j] = temp
  1832.                     i = i+1
  1833.                     j = j-1
  1834.                 end
  1835.             until i > j
  1836.             if (left < j) then
  1837.                 qs1(tablename, left, j)
  1838.             end
  1839.             if (right > i) then
  1840.                 qs1(tablename, i, right)
  1841.             end
  1842.         end
  1843.     end
  1844. end
  1845.  
  1846. function qs2(tablename, left, right, argument)
  1847.     if type(tablename) == 'table' then
  1848.         left = left or 1
  1849.         right = right or #tablename
  1850.         local i,j,x
  1851.         if right-left+1 <= 25 then
  1852.             for i=left+1, right do
  1853.                 x=tablename[i]
  1854.                 j=i-1
  1855.                 while j>=left and x[argument] < tablename[j][argument] do
  1856.                     tablename[j+1]=tablename[j]
  1857.                     j=j-1
  1858.                 end
  1859.                 tablename[j+1]=x
  1860.             end
  1861.         else
  1862.             i,j,x = left, right, tablename[math.floor((left+right)/2)][argument]
  1863.             local temp
  1864.             repeat
  1865.                 while tablename[i][argument]<x and i < right do
  1866.                     i = i+1
  1867.                 end
  1868.                 while tablename[j][argument]>x and j > left do
  1869.                     j = j-1
  1870.                 end
  1871.                 if (i <= j) then
  1872.                     temp = tablename[i]
  1873.                     tablename[i] = tablename[j]
  1874.                     tablename[j] = temp
  1875.                     i = i+1
  1876.                     j = j-1
  1877.                 end
  1878.             until i > j
  1879.             if (left < j) then
  1880.                 qs2(tablename, left, j, argument)
  1881.             end
  1882.             if (right > i) then
  1883.                 qs2(tablename, i, right, argument)
  1884.             end
  1885.         end
  1886.     end
  1887. end
  1888.  
  1889. function qs3(tablename, left, right)
  1890.     if type(tablename) == 'table' then
  1891.         left = left or 1
  1892.         right = right or #tablename
  1893.         local i,j,x
  1894.         if right-left+1 <= 25 then
  1895.             for i=left+1, right do
  1896.                 x=tablename[i]
  1897.                 j=i-1
  1898.                 while j>=left and x>tablename[j] do
  1899.                     tablename[j+1]=tablename[j]
  1900.                     j=j-1
  1901.                 end
  1902.                 tablename[j+1]=x
  1903.             end
  1904.         else
  1905.             i,j,x = left, right, tablename[math.floor((left+right)/2)]
  1906.             local temp
  1907.             repeat
  1908.                 while tablename[i]>x and i < right do
  1909.                     i = i+1
  1910.                 end
  1911.                 while tablename[j]<x and j > left do
  1912.                     j = j-1
  1913.                 end
  1914.                 if (i <= j) then
  1915.                     temp = tablename[i]
  1916.                     tablename[i] = tablename[j]
  1917.                     tablename[j] = temp
  1918.                     i = i+1
  1919.                     j = j-1
  1920.                 end
  1921.             until i > j
  1922.             if (left < j) then
  1923.                 qs3(tablename, left, j)
  1924.             end
  1925.             if (right > i) then
  1926.                 qs3(tablename, i, right)
  1927.             end
  1928.         end
  1929.     end
  1930. end
  1931.  
  1932. function qs4(tablename, left, right, argument)
  1933.     if type(tablename) == 'table' then
  1934.         left = left or 1
  1935.         right = right or #tablename
  1936.         local i,j,x
  1937.         if right-left+1 <= 25 then
  1938.             for i=left+1, right do
  1939.                 x=tablename[i]
  1940.                 j=i-1
  1941.                 while j>=left and x[argument]>tablename[j][argument] do
  1942.                     tablename[j+1]=tablename[j]
  1943.                     j=j-1
  1944.                 end
  1945.                 tablename[j+1]=x
  1946.             end
  1947.         else
  1948.             i,j,x = left, right, tablename[math.floor((left+right)/2)][argument]
  1949.             local temp
  1950.             repeat
  1951.                 while tablename[i][argument]>x and i < right do
  1952.                     i = i+1
  1953.                 end
  1954.                 while tablename[j][argument]<x and j > left do
  1955.                     j = j-1
  1956.                 end
  1957.                 if (i <= j) then
  1958.                     temp = tablename[i]
  1959.                     tablename[i] = tablename[j]
  1960.                     tablename[j] = temp
  1961.                     i = i+1
  1962.                     j = j-1
  1963.                 end
  1964.             until i > j
  1965.             if (left < j) then
  1966.                 qs4(tablename, left, j, argument)
  1967.             end
  1968.             if (right > i) then
  1969.                 qs4(tablename, i, right, argument)
  1970.             end
  1971.         end
  1972.     end
  1973. end
  1974.  
  1975. function bin1(tablename,value)
  1976.     if type(tablename) == 'table' then
  1977.         local left,right = 1, #tablename
  1978.         while left <= right do
  1979.             local mid = math.floor((right+left)/2)
  1980.             if tablename[mid] == value then
  1981.                 return mid
  1982.             end
  1983.             if tablename[mid] > value then
  1984.                 right = mid-1
  1985.             else
  1986.                 left = mid+1
  1987.             end
  1988.         end
  1989.     end
  1990.     return
  1991. end
  1992.  
  1993. function bin2(tablename,value,argument)
  1994.     if type(tablename) == 'table' then
  1995.         local left,right = 1, #tablename
  1996.         while left <= right do
  1997.             local mid = math.floor((right+left)/2)
  1998.             if tablename[mid][argument] == value then
  1999.                 return mid
  2000.             end
  2001.             if tablename[mid][argument] > value then
  2002.                 right = mid-1
  2003.             else
  2004.                 left = mid+1
  2005.             end
  2006.         end
  2007.     end
  2008.     return
  2009. end
  2010.  
  2011. function seq1(tablename,value)
  2012.     if type(tablename) == 'table' then
  2013.         for i,j in ipairs(tablename) do
  2014.             if j == value then
  2015.                 return i
  2016.             end
  2017.         end
  2018.     end
  2019.     return
  2020. end
  2021.  
  2022. function seq2(tablename,value,argument)
  2023.     if type(tablename) == 'table' then
  2024.         for i,j in ipairs(tablename) do
  2025.             if j[argument] == value then
  2026.                 return i
  2027.             end
  2028.         end
  2029.     end
  2030.     return
  2031. end
  2032.  
  2033. function table:newsort(argument, order) --Working
  2034.     if argument == 'asc' or argument == 'desc' then
  2035.         order = argument
  2036.         argument = false
  2037.     end
  2038.     order = order or 'asc'
  2039.     if order == 'asc' then
  2040.         if argument then
  2041.             qs2(self,1,#self,argument)
  2042.         else
  2043.             qs1(self,1,#self)
  2044.         end
  2045.     else
  2046.         if argument then
  2047.             qs4(self,1,#self,argument)
  2048.         else
  2049.             qs3(self,1,#self)
  2050.         end
  2051.     end
  2052. end
  2053.  
  2054. function table:find(value,argument) --Working
  2055.     if argument then
  2056.         return seq2(self,value,argument)
  2057.     end
  2058.     return seq1(self,value)
  2059. end
  2060.  
  2061. function table:findcreature(m,arg)
  2062.     if type(m) == 'userdata' then
  2063.         local name = m.name:lower()
  2064.         if not arg then
  2065.             for i,j in ipairs(self) do
  2066.                 if name == j or m.id == j or m == j then
  2067.                     return i
  2068.                 end
  2069.             end
  2070.         else
  2071.             for i,j in ipairs(self) do
  2072.                 if name == j[arg] or m.id == j[arg] or m == j[arg] then
  2073.                     return i
  2074.                 end
  2075.             end
  2076.         end
  2077.     end
  2078. end
  2079.  
  2080. function table:binaryfind(value,argument) --Working
  2081.     if argument then
  2082.         return bin2(self,value,argument)
  2083.     end
  2084.     return bin1(self,value)
  2085. end
  2086.  
  2087. function usedoor(x,y,z,a)
  2088.     x,y,z = x or $wptx, y or $wpty, z or $wptz
  2089.     if not (x and y and z and tilereachable(x,y,z)) then
  2090.         return false
  2091.     end
  2092.     reachlocation(x,y,z)
  2093.     local doorid, tileinfo = 0
  2094.     local topid = topitem(x,y,z).id
  2095.     local pos
  2096.     if not a then
  2097.         pos = table.binaryfind(closeddoorsids,topid)
  2098.         if pos then
  2099.             a = 'open'
  2100.             doorid = closeddoorsids[pos]
  2101.         else
  2102.             pos = table.binaryfind(openeddoorsids,topid)
  2103.             if pos then
  2104.                 a = 'close'
  2105.                 doorid = openeddoorsids[pos]
  2106.             else
  2107.                 return false
  2108.             end
  2109.         end
  2110.     else
  2111.         if a == 'open' then
  2112.             pos = table.binaryfind(closeddoorsids,topid)
  2113.             if not pos then return false end
  2114.             doorid = closeddoorsids[pos]
  2115.         elseif a == 'close' then
  2116.             pos = table.binaryfind(openeddoorsids,topid)
  2117.             if not pos then return false end
  2118.             doorid = openeddoorsids[pos]
  2119.         end
  2120.     end
  2121.     if a == 'open' then
  2122.         while true do
  2123.             useitem(topid,ground(x,y,z)) waitping()
  2124.             topid = topitem(x,y,z).id
  2125.             if not (topid == 2179 or topid == 2177 or topid == doorid) then
  2126.                 return true
  2127.             end
  2128.         end
  2129.     elseif a == 'close' then
  2130.         local doorpos
  2131.         tileinfo = gettile(x,y,z)
  2132.         for i=1, tileinfo.itemcount do
  2133.             if tileinfo.item[i].id == doorid then
  2134.                 doorpos = i
  2135.                 break
  2136.             end
  2137.         end
  2138.         while true do
  2139.             for i=tileinfo.itemcount,1,-1 do
  2140.                 local infoid = tileinfo.item[i].id
  2141.                 if infoid ~= 99 and not itemproperty(infoid, ITEM_NOTMOVEABLE) then
  2142.                     printerror('There is an item above this door, Neobot is unable to move items above a door.')
  2143.                     return false
  2144.                 --elseif infoid == 99 then
  2145.                 --  printerror('There is a player above this door, Neobot is unable to move players above a door.')
  2146.                 --  return false
  2147.                 end
  2148.             end
  2149.             useitem(topid,ground(x,y,z)) waitping()
  2150.             tileinfo = gettile(x,y,z)
  2151.             topid = tileinfo.item[doorpos].id
  2152.             if topid ~= doorid then
  2153.                 return true
  2154.             end
  2155.         end
  2156.     end
  2157. end
  2158.  
  2159. function findweapon()
  2160.     for i,j in ipairs(axes) do
  2161.         if (j == $rhand.id) then
  2162.             return 'rhand', $rhand
  2163.         end
  2164.         if (j == $lhand.id) then
  2165.             return 'lhand', $lhand
  2166.         end
  2167.     end
  2168.     for i,j in ipairs(swords) do
  2169.         if (j == $rhand.id) then
  2170.             return 'rhand', $rhand
  2171.         end
  2172.         if (j == $lhand.id) then
  2173.             return 'lhand', $lhand
  2174.         end
  2175.     end
  2176.     for i,j in ipairs(clubs) do
  2177.         if (j == $rhand.id) then
  2178.             return 'rhand', $rhand
  2179.         end
  2180.         if (j == $lhand.id) then
  2181.             return 'lhand', $lhand
  2182.         end
  2183.     end
  2184.     for i,j in ipairs(distone) do
  2185.         if (j == $rhand.id) then
  2186.             return 'rhand', $rhand
  2187.         end
  2188.         if (j == $lhand.id) then
  2189.             return 'lhand', $lhand
  2190.         end
  2191.     end
  2192.     for i,j in ipairs(wands) do
  2193.         if (j == $rhand.id) then
  2194.             return 'rhand', $rhand
  2195.         end
  2196.         if (j == $lhand.id) then
  2197.             return 'lhand', $lhand
  2198.         end
  2199.     end
  2200.     for i,j in ipairs(rods) do
  2201.         if (j == $rhand.id) then
  2202.             return 'rhand', $rhand
  2203.         end
  2204.         if (j == $lhand.id) then
  2205.             return 'lhand', $lhand
  2206.         end
  2207.     end
  2208.     for i,j in ipairs(bows) do
  2209.         if (j == $rhand.id) then
  2210.             return 'rhand', $rhand
  2211.         end
  2212.         if (j == $lhand.id) then
  2213.             return 'lhand', $lhand
  2214.         end
  2215.     end
  2216.     if (0 == $rhand.id) then
  2217.         return 'rhand', $rhand
  2218.     end
  2219.     if (0 == $lhand.id) then
  2220.         return 'lhand', $lhand
  2221.     end
  2222. end
  2223.  
  2224. function findweapontouse()
  2225.     local where,id = nil,0
  2226.     if id == 0 then
  2227.         for i,j in ipairs(axes) do if itemcount(j) > 0 then id = j end end
  2228.     end
  2229.     if id == 0 then
  2230.         for i,j in ipairs(swords) do if itemcount(j) > 0 then id = j end end
  2231.     end
  2232.     if id == 0 then
  2233.         for i,j in ipairs(clubs) do if itemcount(j) > 0 then id = j end end
  2234.     end
  2235.     if clientitemhotkey(id) == 'not found' then
  2236.         if $rhand.id == id then
  2237.             where = 'rhand'
  2238.         elseif $lhand.id == id then
  2239.             where = 'lhand'
  2240.         else
  2241.             where = ''
  2242.         end
  2243.     end
  2244.     return where, id
  2245. end
  2246.  
  2247. function findweapontype()
  2248.     for i,j in ipairs(axes) do
  2249.         if (j == $rhand.id) or (j == $lhand.id) then return 'axe' end
  2250.     end
  2251.     for i,j in ipairs(swords) do
  2252.         if (j == $rhand.id) or (j == $lhand.id) then return 'sword' end
  2253.     end
  2254.     for i,j in ipairs(clubs) do
  2255.         if (j == $rhand.id) or (j == $lhand.id) then return 'club' end
  2256.     end
  2257.     for i,j in ipairs(wands) do
  2258.         if (j == $rhand.id) or (j == $lhand.id) then return 'wand' end
  2259.     end
  2260.     for i,j in ipairs(rods) do
  2261.         if (j == $rhand.id) or (j == $lhand.id) then return 'rod' end
  2262.     end
  2263.     for i,j in ipairs(bows) do
  2264.         if (j == $rhand.id) or (j == $lhand.id) then return 'bow' end
  2265.     end
  2266.     for i,j in ipairs(distone) do
  2267.         if (j == $rhand.id) or (j == $lhand.id) then return 'distance weapon' end
  2268.     end
  2269.     return 'no weapon'
  2270. end
  2271.  
  2272. function findshield()
  2273.     local hand = ''
  2274.     for i,j in ipairs(spellbooks) do
  2275.         if (j == $rhand.id) then
  2276.             return 'rhand', $rhand
  2277.         end
  2278.         if (j == $lhand.id) then
  2279.             return 'lhand', $lhand
  2280.         end
  2281.     end
  2282.     for i,j in ipairs(shields) do
  2283.         if (j == $rhand.id) then
  2284.             return 'rhand', $rhand
  2285.         end
  2286.         if (j == $lhand.id) then
  2287.             return 'lhand', $lhand
  2288.         end
  2289.     end
  2290.     if $rhand.id == 0 then
  2291.         return 'rhand', $rhand
  2292.     end
  2293.     if $lhand.id == 0 then
  2294.         return 'lhand', $lhand
  2295.     end
  2296. end
  2297.  
  2298. function getbestspell(name, type)
  2299.     if type == 'strong strike' then
  2300.         return beststrongstrike(name)
  2301.     else
  2302.         return beststrike(name)
  2303.     end
  2304. end
  2305.  
  2306. function bestruneelement(creaturename, disconsiderdamage) --credits to Hardek.
  2307.     if creaturename == '' then return nil end
  2308.     local cre = creatureinfo(creaturename)
  2309.     voc = voc or vocation()
  2310.     strongonly = strongonly or false
  2311.     local best = ''
  2312.     local max = 0
  2313.     local elements = {ice = ($level*0.2)+($mlevel*2.4)+14, fire = ($level*0.2)+($mlevel*2.4)+14, earth = ($level*0.2)+($mlevel*1.2)+7, energy = ($level*0.2)+($mlevel*1.2)+7}
  2314.     if disconsiderdamage then
  2315.         elements = {ice = 0, fire = 0, earth = 0, energy = 0}
  2316.     end
  2317.     for i,j in pairs(elements) do
  2318.         if cre[i..'mod']*j >= max then
  2319.             max = cre[i..'mod']*j
  2320.             best = i
  2321.         end
  2322.     end
  2323.     return best
  2324. end
  2325.  
  2326. function caststrike(a,b)
  2327.     if $attacked.id > 0 then
  2328.         local belement
  2329.         if $attacked.isplayer then
  2330.             belement = 'fire'
  2331.         else
  2332.             belement = bestelement($attacked.name, false)
  2333.         end
  2334.         a,b = a or 900, b or 1100
  2335.         if belement then
  2336.             local bspell = 'exori '..getelementword(belement)
  2337.             if cooleddown(bspell) and $mp >= 20 and $attacked.hppc > 0 and $attacked.dist <= 3 and $attacked.isshootable then
  2338.                 cast(bspell)
  2339.                 wait(a,b)
  2340.                 return true
  2341.             end
  2342.         end
  2343.     end
  2344.     return false
  2345. end
  2346.  
  2347. function caststrongstrike(a,b,c)
  2348.     if $attacked.id > 0 then
  2349.         a,b,c = a or 900, b or 1100, c or 75
  2350.         local voc = vocation()
  2351.         local spell
  2352.         if voc == 'druid' then
  2353.             if $attacked.ismonster then
  2354.                 local temp = creatureinfo($attacked.name)
  2355.                 if cooleddown('strong ice strike') and (temp.icemod >= temp.earthmod or not cooleddown('strong terra strike')) and (temp.icemod >= c) then
  2356.                     spell = 'exori gran frigo'
  2357.                 elseif cooleddown('strong terra strike') and (temp.earthmod >= temp.icemod or not cooleddown('strong ice strike')) and (temp.earthmod >= c) then
  2358.                     spell = 'exori gran tera'
  2359.                 end
  2360.             else
  2361.                 if cooleddown('strong ice strike') then
  2362.                     spell = 'exori gran frigo'
  2363.                 elseif cooleddown('strong terra strike') then
  2364.                     spell = 'exori gran tera'
  2365.                 end
  2366.             end
  2367.         elseif voc == 'sorcerer' then
  2368.             if $attacked.ismonster then
  2369.                 local temp = creatureinfo($attacked.name)
  2370.                 if cooleddown('strong energy strike') and (temp.energymod >= temp.firemod or not cooleddown('strong flame strike')) and (temp.energymod >= c) then
  2371.                     spell = 'exori gran vis'
  2372.                 elseif cooleddown('strong flame strike') and (temp.firemod >= temp.energymod or not cooleddown('strong energy strike')) and (temp.firemod >= c) then
  2373.                     spell = 'exori gran flam'
  2374.                 end
  2375.             else
  2376.                 if cooleddown('strong energy strike') then
  2377.                     spell = 'exori gran vis'
  2378.                 elseif cooleddown('strong flame strike') then
  2379.                     spell = 'exori gran flam'
  2380.                 end
  2381.             end
  2382.         end
  2383.         if spell and cooleddown(spell)  and $mp >= 60 and $attacked.hppc > 0 and $attacked.dist <= 3 and $attacked.isshootable then
  2384.             cast(spell)
  2385.             wait(a,b)
  2386.             return true
  2387.         end
  2388.     end
  2389.     return false
  2390. end
  2391.  
  2392. --[[function caststrongstrike(a,b,c)
  2393.     if $attacked.name ~= '' then
  2394.         local belement, belementmod
  2395.         if $attacked.isplayer then
  2396.             local voc = vocation()
  2397.             if voc == 'druid' then
  2398.                 if cooleddown('strong ice strike') then
  2399.                     belement, belementmod = 'ice', 1000
  2400.                 elseif cooleddown('strong terra strike') then
  2401.                     belement, belementmod = 'earth', 1000
  2402.                 end
  2403.             elseif voc == 'sorcerer' then
  2404.                 if cooleddown('strong flame strike') then
  2405.                     belement, belementmod = 'fire', 1000
  2406.                 elseif cooleddown('strong energy strike') then
  2407.                     belement, belementmod = 'energy', 1000
  2408.                 end
  2409.             end
  2410.         else
  2411.             belement, belementmod = bestelement($attacked.name, true)
  2412.         end
  2413.         a,b = a or 900, b or 1100
  2414.         if belement and (not c or belementmod >= c) then
  2415.             local bspell = 'exori gran '..getelementword(belement)
  2416.             if cooleddown(bspell) and $mp >= 60 and $attacked.hppc > 0 and $attacked.dist <= 3 and $attacked.isshootable then
  2417.                 cast(bspell)
  2418.                 wait(a,b)
  2419.                 return true
  2420.             end
  2421.         end
  2422.     end
  2423.     return false
  2424. end--]]
  2425.  
  2426. function shootbestrune(a,b,cre,disconsider)
  2427.     local runes = {energy = 3174, earth = 3179, fire = 3189, ice = 3158}
  2428.     if type(cre) == 'boolean' then
  2429.         disconsider = cre
  2430.         cre = nil
  2431.     end
  2432.     cre = cre or $attacked
  2433.     a,b = a or 900, b or 1100
  2434.     if cre.id ~= 0 then
  2435.         useoncreature(runes[bestruneelement(cre.name,disconsider)],cre)
  2436.         wait(a,b)
  2437.         return true
  2438.     end
  2439.     return false
  2440. end
  2441.  
  2442. function findcreature(...)
  2443.     local tofind,found = {...},{}
  2444.     table.lower(tofind)
  2445.     local i=1
  2446.     while i <= #tofind do
  2447.         local j = tofind[i]
  2448.         if type(j) == 'userdata' and j.name and j.name ~= '' then
  2449.             table.insert(found,j)
  2450.             table.remove(tofind,i)
  2451.         else
  2452.             i = i+1
  2453.         end
  2454.     end
  2455.     if #tofind > 0 then
  2456.         foreach creature p do
  2457.             if table.find(tofind,p.name:lower()) or table.find(tofind,p.id) then
  2458.                 table.insert(found,p)
  2459.             end
  2460.         end
  2461.     end
  2462.     return table.unpack(found)
  2463. end
  2464.  
  2465. function findcreaturesonspellrange(spelltype,direction,iteratetype)
  2466.     if not iteratetype then
  2467.         iteratetype = 'f'
  2468.     end
  2469.     local found = {}
  2470.     foreach creature p iteratetype do
  2471.         if isonspellarea(p,spelltype,direction) then
  2472.             table.insert(found,p)
  2473.         end
  2474.     end
  2475.     return table.unpack(found)
  2476. end
  2477.  
  2478. function findplayersonspellrange(spelltype,direction)
  2479.     findcreaturesonspellrange(spelltype,direction,'pf')
  2480. end
  2481.  
  2482. function findmonstersonspellrange(spelltype,direction)
  2483.     findcreaturesonspellrange(spelltype,direction,'mf')
  2484. end
  2485.  
  2486. function findcreatureontile(x,y,z)
  2487.     if x == nil or y == nil or z == nil or math.abs($posx-x) > 8 or math.abs($posy-y) > 6 or math.abs($posz-z) > 0 then
  2488.         return
  2489.     end
  2490.     foreach creature fcre 'f' do
  2491.         if fcre.posx == x and fcre.posy == y and fcre.posz == z then
  2492.             return fcre
  2493.         end
  2494.     end
  2495.     return
  2496. end
  2497.  
  2498. function iscreatureontile(x,y,z,ctype)
  2499.     local creatureontileinfo = gettile(x,y,z)
  2500.     if creatureontileinfo then
  2501.         for i=2, creatureontileinfo.itemcount do
  2502.             if creatureontileinfo.item[i].id == 99 and ((not ctype or ctype == 'any') or (ctype == 'player' and creatureontileinfo.item[i].count <= 0x40000000) or (ctype == 'monster' and creatureontileinfo.item[i].count > 0x40000000)) then
  2503.                 return true
  2504.             end
  2505.         end
  2506.     end
  2507.     return false
  2508. end
  2509.  
  2510. function iscreatureshootable(n)
  2511.     if type(n) ~= 'userdata' then
  2512.         n = findcreature(n)
  2513.     end
  2514.     if n ~= nil then
  2515.         if tileshootable(n.posx,n.posy,n.posz) then
  2516.             return true
  2517.         else
  2518.             return false
  2519.         end
  2520.     end
  2521. end
  2522.  
  2523. function iscreaturereachable(n)
  2524.     if type(n) ~= 'userdata' then
  2525.         n = findcreature(n)
  2526.     end
  2527.     if n ~= nil then
  2528.         if tilereachable(n.posx,n.posy,n.posz) then
  2529.             return true
  2530.         else
  2531.             return false
  2532.         end
  2533.     end
  2534. end
  2535.  
  2536. function refillammo()
  2537.     local ammo = {761, 762, 763, 774, 1781, 2992, 3277, 3287, 3298, 3347, 3446, 3447, 3448, 3449, 3450, 6528, 7363, 7364, 7365, 7366, 7367, 7368, 7378}
  2538.     local i = 1
  2539.     while ammo[i] do
  2540.         if $rhand.id == ammo[i] and $rhand.count < 100 then
  2541.             equipitem(ammo[i],"rhand",'0-15',100)
  2542.             waitping()
  2543.             return
  2544.         elseif $lhand.id == ammo[i] and $lhand.count < 100 then
  2545.             equipitem(ammo[i],"lhand",'0-15',100)
  2546.             waitping()
  2547.             return
  2548.         elseif $belt.id == ammo[i] and $belt.count < 100 then
  2549.             equipitem(ammo[i],"belt",'0-15',100)
  2550.             waitping()
  2551.             return
  2552.         end
  2553.         i = i+1
  2554.     end
  2555. end
  2556.  
  2557. function color(r,g,b,transparency)
  2558.     if type(r) ~= 'string' then
  2559.         transparency = transparency or 0
  2560.         return (math.floor(transparency*2.55)*16777216) + (r*65536) + (g*256) + b
  2561.     else
  2562.         r = r:gsub(' ','_')
  2563.         r = r:gsub('-','_')
  2564.         g = g or 0
  2565.         local colors = {amaranth = 0xE52B50, amber = 0xFFBF00, aquamarine = 0x7FFFD4, azure = 0x007FFF, baby_blue = 0x89CFF0, beige = 0xF5F5DC, black = 0x000000, blue = 0x0000FF, blue_green = 0x0095B6, blue_violet = 0x8A2BE2, bronze = 0xCD7F32, brown = 0xA52A2A, byzantium = 0x702963, barmine = 0x960018, cerise = 0xDE3163, cerulean = 0x007BA7, champagne = 0xF7E7CE, chartreuse_green = 0x7FFF00, copper = 0xB87333, coral = 0xF88379, crimson = 0xDC143C, cyan = 0x00FFFF, electric_blue = 0x7DF9FF, erin = 0x00FF3F, gold = 0xFFD700, gray = 0x808080, green = 0x00CC00, harlequin = 0x3FFF00, indigo = 0x4B0082, ivory = 0xFFFFF0, jade = 0x00A86B, lavender = 0xB57EDC, lilac = 0xC8A2C8, lime = 0xBFFF00, magenta = 0xFF00FF, magenta_rose = 0xFF00AF, maroon = 0x800000, mauve = 0xE0B0FF, navy_blue = 0x000080, olive = 0x808000, orange = 0xFFA500, orange_red = 0xFF4500, op = 0x6FFFFFF, peach = 0xFFE5B4, persian_blue = 0x1C39BB, pink = 0xFFC0CB, plum = 0x8E4585, prussian_blue = 0x003153, pen = 0x5410987, pumpkin = 0xFF7518, purple = 0x800080, raspberry = 0xE30B5C, red = 0xFF0000, red_violet = 0xC71585, rose = 0xFF007F, salmon = 0xFA8072, scarlet = 0xFF2400, silver = 0xC0C0C0, slate_gray = 0x708090, spring_green = 0x00FF7F, taupe = 0x483C32, teal = 0x008080, turquoise = 0x40E0D0, violet = 0xEE82EE, viridian = 0x40826D, white = 0xFFFFFF, yellow = 0xFFFF00}
  2566.         if colors[r] then
  2567.             return colors[r] + (math.floor(2.55*g)*16777216)
  2568.         else
  2569.             return colors.white + (math.floor(2.55*g)*16777216)
  2570.         end
  2571.     end
  2572. end
  2573.  
  2574. function moveitemsupto(itemname, amount, to, from)
  2575.     itemname = itemid(itemname)
  2576.     if not to or (type(to) ~= 'number' and type(to) ~= 'string') then
  2577.         to = 'backpack'
  2578.     end
  2579.     if not from or (type(from) ~= 'number' and type(from) ~= 'string') then
  2580.         from = ''
  2581.     end
  2582.     if (type(to) == 'string' and to:find('ground')) or (type(from) == 'string' and from:find('ground')) then
  2583.         return false
  2584.     end
  2585.     while itemcount(itemname, to) < amount and itemcount(itemname, from) > 0 do
  2586.         moveitems(itemname, to, from, amount-itemcount(itemname,to))
  2587.         waitping()
  2588.     end
  2589. end
  2590.  
  2591. function moveitemsdownto(itemname, amount, from, to)
  2592.     itemname = itemid(itemname)
  2593.     if not to or (type(to) ~= 'number' and type(to) ~= 'string') then
  2594.         to = ''
  2595.     end
  2596.     if not from or (type(from) ~= 'number' and type(from) ~= 'string') then
  2597.         from = 'backpack'
  2598.     end
  2599.     while itemcount(itemname, from) > amount do
  2600.         moveitems(itemname, to, from, amount-itemcount(itemname,from))
  2601.         waitping()
  2602.     end
  2603. end
  2604.  
  2605. function buyitemsupto(itemname, amount, currentamount)
  2606.     currentamount = currentamount or itemcount(itemname)
  2607.     if not $tradeopen then opentrade() end
  2608.     amount = amount-currentamount
  2609.     --[[if tradecount('buy',itemname) == 0 then itemname = itemid(itemname) end--]]
  2610.     while amount > 0 --[[and (tradecount('buy',itemname) >= amount or tradecount('buy',itemname) == 100)--]] do
  2611.         buyitems(itemname, amount)
  2612.         waitping(3,4)
  2613.         amount = amount-100
  2614.     end
  2615. end
  2616.  
  2617. function sellitemsdownto(itemname, amount, currentamount)
  2618.     currentamount = currentamount or itemcount(itemname)
  2619.     if not $tradeopen then opentrade() end
  2620.     currentamount = currentamount-amount
  2621.     --[[if tradecount('sell',itemname) == 0 then itemname = itemid(itemname) end--]]
  2622.     while currentamount > 0 --[[and (tradecount('sell',itemname) >= currentamount or tradecount('sell',itemname) == 100)--]] do
  2623.         sellitems(itemname, currentamount)
  2624.         waitping(3,4)
  2625.         currentamount = currentamount-100
  2626.     end
  2627. end
  2628.  
  2629. function buyitemstocap(itemname, captosave)
  2630.     local amount = math.floor(($cap-captosave)/itemweight(itemname))
  2631.     opentrade()
  2632.     while amount > 0 do
  2633.         buyitems(itemname,amount)
  2634.         waitping(3,4)
  2635.         amount = amount-100
  2636.     end
  2637. end
  2638.  
  2639. function sellflasks()
  2640.     if not $tradeopen then opentrade() end
  2641.     for i=283,285 do
  2642.         local count = tradecount('sell',i)
  2643.         while count > 0 do
  2644.             sellitems(i,count) waitping()
  2645.             count = tradecount('sell',i)
  2646.         end
  2647.     end
  2648. end
  2649.  
  2650. function levitate(direction,updown)
  2651.     local dir = {x = {n = 0, s = 0, w = -1, e = 1},
  2652.                  y = {n = -1, s = 1, w = 0, e = 0}}
  2653.     if direction == 'w' or direction == 'e' or direction == 'n' or direction == 's' then
  2654.         local startposz,tries,maxtries = $posz,0,math.random(4,6)
  2655.         if not updown or (updown ~= 'up' and updown ~= 'down') then
  2656.             local tile = gettile($posx+dir.x[direction],$posy+dir.y[direction],$posz)
  2657.             updown = 'up'
  2658.             if tile.itemcount == 0 or (tile.itemcount == 1 and not itemproperty(tile.item[1].id,ITEM_NOTROOFEDGE)) then
  2659.                 updown = 'down'
  2660.             end
  2661.         end
  2662.         while $mp >= 50 and $level >= 12 and $posz == startposz and tries < maxtries and cooleddown('levitate') do
  2663.             while (direction ~= $self.dir) do turn(direction) waitping(1.2,1.4) end
  2664.             cast('exani hur '..updown)
  2665.             waitping()
  2666.             tries=tries+1
  2667.         end
  2668.         if $posz ~= startz then
  2669.             return true
  2670.         end
  2671.     end
  2672.     return false
  2673. end
  2674. --351~355
  2675. function pick(x,y,z,holes)
  2676.     x,y,z = x or $wptx, y or $wpty, z or $wptz
  2677.     holes = holes or {394}
  2678.     local pickid = 3456
  2679.     local k = ''
  2680.     reachlocation(x,y,z)
  2681.     if x and y and z and math.abs($posx-x) <= 7 and math.abs($posy-y) <= 5 and $posz == z and ($posx ~= x or $posy ~= y) then
  2682.         local tile = gettile(x,y,z)
  2683.         local id = topitem(x,y,z).id
  2684.         if tile.item[1].id >= 351 and tile.item[1].id <= 355 then
  2685.             for i=2, tile.itemcount do
  2686.                 if itemproperty(tile.item[i].id, ITEM_NOTMOVEABLE) then
  2687.                     return false
  2688.                 end
  2689.             end
  2690.             while id ~= 394 do
  2691.                 while id > 355 or id < 351 do
  2692.                     if not itemproperty(id,ITEM_NOTMOVEABLE) then
  2693.                         moveitems(id,ground($posx,$posy,$posz),ground(x,y,z),100) waitping(1,1.3) id = topitem(x,y,z).id
  2694.                     else
  2695.                         return false
  2696.                     end
  2697.                 end
  2698.                 while id ~= 394 and itemproperty(id, ITEM_GROUND) do
  2699.                     if iscreatureontile(x,y,z) then
  2700.                         local dir, dirx, diry = wheretomoveitem(x,y,z,99)
  2701.                         moveitems(99,ground(x+dirx,y+diry,z),ground(x,y,z),100) wait(1400,1600)
  2702.                     elseif clientitemhotkey(pickid,'crosshair') == 'not found' and itemcount(pickid) == 0 then
  2703.                         printerror('Pick not found.')
  2704.                         return false
  2705.                     end
  2706.                     useitemon(pickid,id,ground(x,y,z),k) wait(900,1100)
  2707.                     id = topitem(x,y,z).id
  2708.                 end
  2709.             end
  2710.             wait(100)
  2711.             id = topitem(x,y,z).id
  2712.         end
  2713.     end
  2714.     return false
  2715. end
  2716.  
  2717. function openhole(x,y,z,holes)
  2718.     x,y,z = x or $wptx, y or $wpty, z or $wptz
  2719.     holes = holes or {{593,594}, {606, 607}, {608, 609}, {867, 868}}
  2720.     local shovelid = false
  2721.     for i,j in ipairs(shovels) do
  2722.         if itemcount(j) > 0 then
  2723.             shovelid = j
  2724.             break
  2725.         end
  2726.     end
  2727.     if not shovelid then
  2728.         for i,j in ipairs(shovels) do
  2729.             if clientitemhotkey(j) ~= 'not found' then
  2730.                 shovelid = j
  2731.                 break
  2732.             end
  2733.         end
  2734.     end
  2735.     local k = ''
  2736.     if not shovelid then return false end
  2737.     reachlocation(x,y,z)
  2738.     if x and y and z and math.abs($posx-x) <= 7 and math.abs($posy-y) <= 5 and $posz == z and ($posx ~= x or $posy ~= y) then
  2739.         local v = 1
  2740.         while v <= #holes and not isitemontile(holes[v][1],x,y,z) do
  2741.             v = v+1
  2742.         end
  2743.         if v <= #holes then
  2744.             local id = topitem(x,y,z).id
  2745.             while id ~= holes[v][2] do
  2746.                 if id == holes[v][1] then
  2747.                     if iscreatureontile(x,y,z) then
  2748.                         local dir, dirx, diry = wheretomoveitem(x,y,z,99)
  2749.                         moveitems(99,ground(x+dirx,y+diry,z),ground(x,y,z),100) wait(1400,1600)
  2750.                     elseif clientitemhotkey(shovelid,'crosshair') == 'not found' and itemcount(shovelid) == 0 then
  2751.                         printerror(shoveltype.. ' not found.')
  2752.                         return false
  2753.                     end
  2754.                     useitemon(shovelid,id,ground(x,y,z),k) wait(900,1100)
  2755.                 elseif not itemproperty(id,ITEM_NOTMOVEABLE) then
  2756.                     moveitems(id,ground($posx,$posy,$posz),ground(x,y,z),100) waitping(1,1.3)
  2757.                 else
  2758.                     return false
  2759.                 end
  2760.                 id = topitem(x,y,z).id
  2761.             end
  2762.             return true
  2763.         end
  2764.     end
  2765.     return false
  2766. end
  2767.  
  2768. function opensand(x,y,z)
  2769.     return openhole(x,y,z, {{231,615}})
  2770. end
  2771.  
  2772. function usesewer(x,y,z,sewers)
  2773.     x,y,z = x or $wptx, y or $wpty, z or $wptz
  2774.     sewers = sewers or {435}
  2775.     reachlocation(x,y,z)
  2776.     if x and y and z and math.abs($posx-x) <= 7 and math.abs($posy-y) <= 5 and $posz == z and ($posx ~= x or $posy ~= y) then
  2777.         local v = 1
  2778.         while v <= #sewers and not isitemontile(sewers[v],x,y,z) do
  2779.             v = v+1
  2780.         end
  2781.         if v <= #sewers then
  2782.             local id = topitem(x,y,z).id
  2783.             while $posz == z do
  2784.                 if id == sewers[v] then
  2785.                     useitem(sewers[v],ground(x,y,z)) wait(300,500)
  2786.                 elseif not itemproperty(id,ITEM_NOTMOVEABLE) then
  2787.                     moveitems(id,ground($posx,$posy,$posz),ground(x,y,z),100) waitping(1,1.3)
  2788.                 else
  2789.                     return false
  2790.                 end
  2791.                 id = topitem(x,y,z).id
  2792.             end
  2793.             return true
  2794.         end
  2795.     end
  2796.     return false
  2797. end
  2798.  
  2799. function uselever(x,y,z,id)
  2800.     x,y,z = x or $wptx, y or $wpty, z or $wptz
  2801.     local levers = {2771, 2772}
  2802.     if id then
  2803.         levers = {id}
  2804.     end
  2805.     reachlocation(x,y,z)
  2806.     local cur = {$posx,$posy,$posz}
  2807.     if x and y and z and math.abs($posx-x) <= 7 and math.abs($posy-y) <= 5 and $posz == z and ($posx ~= x or $posy ~= y) then
  2808.         local v = 1
  2809.         while v <= #levers and not isitemontile(levers[v],x,y,z) do
  2810.             v = v+1
  2811.         end
  2812.         if v <= #levers then
  2813.             local id = topitem(x,y,z).id
  2814.             while isitemontile(levers[v],x,y,z) and (cur[1] == $posx and cur[2] == $posy and cur[3] == $posz) do
  2815.                 if id == levers[v] then
  2816.                     useitem(levers[v],ground(x,y,z)) wait(300,500)
  2817.                 elseif not itemproperty(id,ITEM_NOTMOVEABLE) then
  2818.                     moveitems(id,ground($posx,$posy,$posz),ground(x,y,z),100) waitping(1,1.3)
  2819.                 else
  2820.                     return false
  2821.                 end
  2822.                 id = topitem(x,y,z).id
  2823.             end
  2824.             return true
  2825.         end
  2826.     end
  2827.     return false
  2828. end
  2829.  
  2830. function breakdworcwall(x,y,z, walls)
  2831.     x,y,z = x or $wptx, y or $wpty, z or $wptz
  2832.     walls = walls or {{2295, 3146}, {2296, 3145}}
  2833.     local sneakies = {9594, 9596, 9598}
  2834.     local weaponlocation,weaponid = findweapontouse()
  2835.     if clientitemhotkey(weaponid,'crosshair') ~= 'not found' then
  2836.         weaponlocation = ''
  2837.     end
  2838.     if weaponid == 0 then
  2839.         return false
  2840.     end
  2841.     print(weaponid)
  2842.     reachlocation(x,y,z)
  2843.     if x and y and z and math.abs($posx-x) <= 7 and math.abs($posy-y) <= 5 and $posz == z and ($posx ~= x or $posy ~= y) then
  2844.         local v = 1
  2845.         while v <= #walls and not isitemontile(walls[v][1],x,y,z) do
  2846.             v = v+1
  2847.         end
  2848.         if v <= #walls then
  2849.             local id = topitem(x,y,z).id
  2850.             while id ~= walls[v][2] do
  2851.                 if id == walls[v][1] then
  2852.                     if iscreatureontile(x,y,z) then
  2853.                         local dir, dirx, diry = wheretomoveitem(x,y,z,99)
  2854.                         moveitems(99,ground(x+dirx,y+diry,z),ground(x,y,z),100) wait(1400,1600)
  2855.                     elseif clientitemhotkey(weaponid,'crosshair') == 'not found' and itemcount(weaponid) == 0 then
  2856.                         printerror('Weapon not found.')
  2857.                         return false
  2858.                     end
  2859.                     useitemon(weaponid,id,ground(x,y,z),weaponlocation) wait(900,1100)
  2860.                 elseif not itemproperty(id,ITEM_NOTMOVEABLE) then
  2861.                     moveitems(id,ground($posx,$posy,$posz),ground(x,y,z),100) waitping(1,1.3)
  2862.                 else
  2863.                     return false
  2864.                 end
  2865.                 id = topitem(x,y,z).id
  2866.             end
  2867.             return true
  2868.         end
  2869.     end
  2870.     return false
  2871. end
  2872.  
  2873. function breakspidersilk(x,y,z, walls)
  2874.     x,y,z = x or $wptx, y or $wpty, z or $wptz
  2875.     walls = walls or {{182, 188}, {183, 189}}
  2876.     local weaponid,weaponlocation = 5467
  2877.     if itemcount(5467) > 0 then
  2878.         if clientitemhotkey(weaponid,'crosshair') == 'not found' then
  2879.             if $rhand.id == weaponid then
  2880.                 weaponlocation = 'rhand'
  2881.             elseif $lhand.id == weaponid then
  2882.                 weaponlocation = 'lhand'
  2883.             else
  2884.                 weaponlocation = ''
  2885.             end
  2886.         end
  2887.     else
  2888.         weaponlocation,weaponid = findweapontouse()
  2889.         if clientitemhotkey(weaponid,'crosshair') ~= 'not found' then
  2890.             weaponlocation = ''
  2891.         end
  2892.     end
  2893.     if weaponid == 0 then
  2894.         return false
  2895.     end
  2896.     reachlocation(x,y,z)
  2897.     if x and y and z and math.abs($posx-x) <= 7 and math.abs($posy-y) <= 5 and $posz == z and ($posx ~= x or $posy ~= y) then
  2898.         local v = 1
  2899.         while v <= #walls and not isitemontile(walls[v][1],x,y,z) do
  2900.             v = v+1
  2901.         end
  2902.         if v <= #walls then
  2903.             local id = topitem(x,y,z).id
  2904.             while id ~= walls[v][2] do
  2905.                 if id == walls[v][1] then
  2906.                     if iscreatureontile(x,y,z) then
  2907.                         local dir, dirx, diry = wheretomoveitem(x,y,z,99)
  2908.                         moveitems(99,ground(x+dirx,y+diry,z),ground(x,y,z),100) wait(1400,1600)
  2909.                     elseif clientitemhotkey(weaponid,'crosshair') == 'not found' and itemcount(weaponid) == 0 then
  2910.                         printerror('Weapon not found.')
  2911.                         return false
  2912.                     end
  2913.                     useitemon(weaponid,id,ground(x,y,z),weaponlocation) wait(900,1100)
  2914.                 elseif not itemproperty(id,ITEM_NOTMOVEABLE) then
  2915.                     moveitems(id,ground($posx,$posy,$posz),ground(x,y,z),100) waitping(1,1.3)
  2916.                 else
  2917.                     return false
  2918.                 end
  2919.                 id = topitem(x,y,z).id
  2920.             end
  2921.             return true
  2922.         end
  2923.     end
  2924.     return false
  2925. end
  2926.  
  2927. function cutgrass(x,y,z)
  2928.     x,y,z = x or $wptx, y or $wpty, z or $wptz
  2929.     local grasses = {{3702, 3701},{3696, 3695}}
  2930.     local weaponid,weaponlocation = false
  2931.     for i,j in ipairs(machetes) do
  2932.         if itemcount(j) > 0 then
  2933.             weaponid = j
  2934.             break
  2935.         end
  2936.     end
  2937.     if not macheteid then
  2938.         for i,j in ipairs(machetes) do
  2939.             if clientitemhotkey(j) ~= 'not found' then
  2940.                 weaponid = j
  2941.                 break
  2942.             end
  2943.         end
  2944.     end
  2945.     if not weaponlocation then
  2946.         if $rhand.id == weaponid then
  2947.             weaponlocation = 'rhand'
  2948.         elseif $lhand.id == weaponid then
  2949.             weaponlocation = 'lhand'
  2950.         else
  2951.             weaponlocation = ''
  2952.         end
  2953.     end
  2954.     if not weaponid then
  2955.         return false
  2956.     end
  2957.     reachlocation(x,y,z)
  2958.     if x and y and z and math.abs($posx-x) <= 7 and math.abs($posy-y) <= 5 and $posz == z and ($posx ~= x or $posy ~= y) then
  2959.         local v = 1
  2960.         while v <= #grasses and not isitemontile(grasses[v][1],x,y,z) do
  2961.             v = v+1
  2962.         end
  2963.         if v <= #grasses then
  2964.             local id = topitem(x,y,z).id
  2965.             while id ~= grasses[v][2] do
  2966.                 if id == grasses[v][1] then
  2967.                     if iscreatureontile(x,y,z) then
  2968.                         local dir, dirx, diry = wheretomoveitem(x,y,z,99)
  2969.                         moveitems(99,ground(x+dirx,y+diry,z),ground(x,y,z),100) wait(1400,1600)
  2970.                     elseif clientitemhotkey(weaponid,'crosshair') == 'not found' and itemcount(weaponid) == 0 then
  2971.                         printerror('Machete not found.')
  2972.                         return false
  2973.                     end
  2974.                     useitemon(weaponid,id,ground(x,y,z),weaponlocation) wait(900,1100)
  2975.                 elseif not itemproperty(id,ITEM_NOTMOVEABLE) then
  2976.                     moveitems(id,ground($posx,$posy,$posz),ground(x,y,z),100) waitping(1,1.3)
  2977.                 else
  2978.                     return false
  2979.                 end
  2980.                 id = topitem(x,y,z).id
  2981.             end
  2982.             return true
  2983.         end
  2984.     end
  2985.     return false
  2986. end
  2987.  
  2988. function pickupitems(dir,n,amount)
  2989.     local dire = {dirs = {'c', 'n', 's', 'w', 'e', 'nw', 'ne', 'sw', 'se'},
  2990.                   x = {c = 0, n = 0, s = 0, w = -1, e = 1, nw = -1, ne = 1, sw = -1, se = 1},
  2991.                   y = {c = 0, n = -1, s = 1, w = 0, e = 0, nw = -1, ne = -1, sw = 1, se = 1}}
  2992.     if not dir or not table.find(dire.dirs,dir) then
  2993.         if type(n) == 'number' then
  2994.             amount = n
  2995.         end
  2996.         if not n then
  2997.             n = dir
  2998.         end
  2999.         dir = 'c'
  3000.     end
  3001.     if not n then
  3002.         n = ''
  3003.     end
  3004.     if not amount then
  3005.         amount = 100
  3006.     end
  3007.     local pos = {x = $posx+dire.x[dir], y = $posy+dire.y[dir], z = $posz}
  3008.     local topid = topitem(pos.x,pos.y,pos.z).id
  3009.     if topid ~= 0 and itemproperty(topid,ITEM_PICKUPABLE) then
  3010.         moveitems(topid,n,ground(pos.x,pos.y,pos.z),amount)
  3011.     end
  3012. end
  3013.  
  3014. --local ropeholesids = {386, 421, 7762, 12202}
  3015. local stairsids = {386, 421, 1948, 1968, 5542, 7762, 7771, 9116, 12202}
  3016. local bodies = {stakeable = {{4097, 5995, 'demon'}, {4137, 6006, 'vampire'}}, skinnable = {{4173, 6017, 'rabbit'}, {4011, 5969, 'minotaur'}, {4025, 5973, 'dragon'}, {4047, 5981, 'minotaur mage'}, {4052, 5982, 'minotaur archer'}, {4057, 5983, 'minotaur guard'}, {4062, 5984, 'dragon lord'}, {4112, 5999, 'behemoth'}, {4212, 6030, 'bonebeast'}, {4321, 4239, 'lizard templar'}, {4324, 6040, 'lizard sentinel'}, {4327, 6041, 'lizard snakecharmer'}, {10352, 10355, 'lizard high guard'}, {10356, 10359, 'lizard legionnaire'}, {10360, 10363, 'lizard dragon priest'}, {10364, 10367, 'lizard zaogun'}, {10368, 10371, 'lizard chosen'}}}
  3017.  
  3018. BODYLIST = {}
  3019.  
  3020. function BODYLIST:new(n)
  3021.     n = n or {}
  3022.     setmetatable(n, self)
  3023.     self.__index = self
  3024.     return n
  3025. end
  3026.  
  3027. function itemproperties(iid, ...)
  3028.     iid = itemid(iid)
  3029.     local properties = {...}
  3030.     for i,j in ipairs(properties) do
  3031.         if not itemproperty(iid, j) then
  3032.             return false
  3033.         end
  3034.     end
  3035.     return true
  3036. end
  3037.  
  3038. function BODYLIST:clear(n)
  3039.     self = {}
  3040. end
  3041.  
  3042. function BODYLIST:remove(...)
  3043.     local args = {...}
  3044.     for i,j in ipairs(args) do
  3045.         local temp = table.find(self, j, 3)
  3046.         if temp then
  3047.             table.remove(self, temp)
  3048.         end
  3049.     end
  3050. end
  3051.  
  3052. function BODYLIST:addid(...)
  3053.     local args = {...}
  3054.     for i,j in ipairs(args) do
  3055.         table.insert(self, {j[1], j[2], j[3]})
  3056.     end
  3057. end
  3058.  
  3059. function BODYLIST:__tostring()
  3060.     toprint = ''
  3061.     for i,j in ipairs(self) do
  3062.         toprint = toprint..j[3]..', '
  3063.     end
  3064.     return toprint:sub(1,#toprint-2)
  3065. end
  3066.  
  3067. function resetbodylists()
  3068.     SKINLIST, STAKELIST = nil, nil
  3069.     SKINLIST = BODYLIST:new({{4011, 5969, 'minotaur'}, {4025, 5973, 'dragon'}, {4047, 5981, 'minotaur mage'}, {4052, 5982, 'minotaur archer'}, {4057, 5983, 'minotaur guard'}, {4062, 5984, 'dragon lord'}, {4112, 5999, 'behemoth'}, {4212, 6030, 'bonebeast'}, {4321, 4239, 'lizard templar'}, {4324, 6040, 'lizard sentinel'}, {4327, 6041, 'lizard snakecharmer'}, {10352, 10355, 'lizard high guard'}, {10356, 10359, 'lizard legionnaire'}, {10360, 10363, 'lizard dragon priest'}, {10364, 10367, 'lizard zaogun'}, {10368, 10371, 'lizard chosen'}})
  3070.     STAKELIST = BODYLIST:new(bodies.stakeable)
  3071. end
  3072.  
  3073. SKINLIST = BODYLIST:new({{4011, 5969, 'minotaur'}, {4025, 5973, 'dragon'}, {4047, 5981, 'minotaur mage'}, {4052, 5982, 'minotaur archer'}, {4057, 5983, 'minotaur guard'}, {4062, 5984, 'dragon lord'}, {4112, 5999, 'behemoth'}, {4212, 6030, 'bonebeast'}, {4321, 4239, 'lizard templar'}, {4324, 6040, 'lizard sentinel'}, {4327, 6041, 'lizard snakecharmer'}, {10352, 10355, 'lizard high guard'}, {10356, 10359, 'lizard legionnaire'}, {10360, 10363, 'lizard dragon priest'}, {10364, 10367, 'lizard zaogun'}, {10368, 10371, 'lizard chosen'}})
  3074. STAKELIST = BODYLIST:new(bodies.stakeable)
  3075.  
  3076. function STAKELIST:add(...)
  3077.     local args = {...}
  3078.     for i,j in ipairs(args) do
  3079.         local temp = table.find(bodies.stakeable, j, 3)
  3080.         if temp and not table.find(self, j, 3) then
  3081.             table.insert(self, bodies.stakeable[temp])
  3082.         end
  3083.     end
  3084. end
  3085.  
  3086. function SKINLIST:add(...)
  3087.     local args = {...}
  3088.     for i,j in ipairs(args) do
  3089.         local temp = table.find(bodies.skinnable, j, 3)
  3090.         if temp and not table.find(self, j, 3) then
  3091.             table.insert(self, {table.unpack(bodies.skinnable[temp])})
  3092.         end
  3093.     end
  3094. end
  3095.  
  3096. function skinspotssample(dist, movebody, waitfresh, bodytable)
  3097.     movebody = movebody or false
  3098.     waitfresh = waitfresh or false
  3099.     if not dist or dist > 7 or dist < 1 then
  3100.         dist = 7
  3101.     end
  3102.     local counter = 0
  3103.     for j=-dist, dist do
  3104.         for i=-dist, dist do
  3105.             local pos = {x = $posx+i, y = $posy+j, z = $posz}
  3106.             if tilehasinfo(pos.x,pos.y,pos.z) and tilereachable(pos.x,pos.y,pos.z) then
  3107.                 local tile, topid, gonextsqm = gettile(pos.x,pos.y,pos.z), topitem(pos.x,pos.y,pos.z).id, false
  3108.                 local tablepos, notmoveablepos = table.find(bodytable, topid, 1)
  3109.                 if waitfresh then
  3110.                     tablepos = tablepos or table.find(bodytable, topid, 2)
  3111.                 end
  3112.                 for k=1, tile.itemcount do
  3113.                     topid = tile.item[k].id
  3114.                     if topid == 99 or table.find(stairsids, topid) then
  3115.                         gonextsqm = true
  3116.                         break
  3117.                     end
  3118.                     if itemproperty(topid, ITEM_NOTMOVEABLE) and not itemproperty(topid, ITEM_GROUND) then
  3119.                         notmoveablepos = k
  3120.                     end
  3121.                     if movebody then
  3122.                         for p,q in ipairs(bodytable) do
  3123.                             if (q[1] == topid or (waitfresh and q[2] == topid)) and (not notmoveablepos or k < notmoveablepos) then
  3124.                                 counter = counter+1
  3125.                             end
  3126.                         end
  3127.                     end
  3128.                 end
  3129.                 if not gonextsqm and not movebody and tablepos then
  3130.                     counter = counter+1
  3131.                 end
  3132.             end
  3133.         end
  3134.     end
  3135.     return counter
  3136. end
  3137.  
  3138. function skinspots(dist, movebody, waitfresh, bodytable)
  3139.     if type(movebody) ~= 'boolean' then
  3140.         movebody = false
  3141.     end
  3142.     if type(waitfresh) ~= 'boolean' then
  3143.         waitfresh = false
  3144.     end
  3145.     return skinspotssample(dist, movebody, waitfresh, SKINLIST)
  3146. end
  3147.  
  3148. function stakespots(dist, movebody, waitfresh, bodytable)
  3149.     if type(movebody) ~= 'boolean' then
  3150.         movebody = false
  3151.     end
  3152.     if type(waitfresh) ~= 'boolean' then
  3153.         waitfresh = false
  3154.     end
  3155.     return skinspotssample(dist, movebody, waitfresh, STAKELIST)
  3156. end
  3157.  
  3158. function skinkitchenknifespots(dist, movebody, waitfresh, bodytable)
  3159.     if type(movebody) ~= 'boolean' then
  3160.         movebody = false
  3161.     end
  3162.     if type(waitfresh) ~= 'boolean' then
  3163.         waitfresh = false
  3164.     end
  3165.     return skinspotssample(dist, movebody, waitfresh, {{4173, 6017, 'rabbit'}})
  3166. end
  3167.  
  3168. function skinsample(dist,movebody,waitfresh,touseid,bodytable)
  3169.     movebody = movebody or false
  3170.     waitfresh = waitfresh or false
  3171.     if not dist or dist < 1 or dist > 7 then
  3172.         dist = 7
  3173.     end
  3174.     touseid = itemid(touseid)
  3175.     local itempos = ''
  3176.     if clientitemhotkey(touseid,'crosshair') == 'not found' then
  3177.         if itemcount(touseid) == 0 then
  3178.             return false
  3179.         end
  3180.     end
  3181.     local pos = {x=nil,y=nil,z=$posz,body=nil,fresh=nil}
  3182.     local cur = {x=nil,y=nil,z=$posz,id=nil}
  3183.     local t = {}
  3184.    
  3185.     local i,j
  3186.     for a=1,dist do
  3187.         j = -a
  3188.         while j <= a do
  3189.             i = -a
  3190.             while i <= a do
  3191.                 cur.x,cur.y = $posx+i,$posy+j
  3192.                 if tilehasinfo(cur.x,cur.y,cur.z) and tilereachable(cur.x,cur.y,cur.z) then
  3193.                     local gonextsqm, tile, tempid = false, gettile(cur.x,cur.y,cur.z), topitem(cur.x,cur.y,cur.z).id
  3194.                     local tablepos, notmoveablepos = table.find(bodytable, tempid, 1)
  3195.                     if waitfresh then
  3196.                         tablepos = tablepos or table.find(bodytable, tempid, 2)
  3197.                     end
  3198.                     for k=1, tile.itemcount do
  3199.                         tempid = tile.item[k].id
  3200.                         if tempid == 99 or table.find(stairsids, tempid) then
  3201.                             gonextsqm = true
  3202.                             break
  3203.                         end
  3204.                         if itemproperty(tempid, ITEM_NOTMOVEABLE) and not itemproperty(tempid, ITEM_GROUND) then
  3205.                             notmoveablepos = k
  3206.                         end
  3207.                         if movebody and not tablepos then
  3208.                             for p,q in ipairs(bodytable) do
  3209.                                 if (q[1] == tempid or (waitfresh and q[2] == tempid)) and (not notmoveablepos or k < notmoveablepos) then
  3210.                                     tablepos = p
  3211.                                 end
  3212.                             end
  3213.                         end
  3214.                     end
  3215.                     if not gonextsqm and tablepos then
  3216.                         pos.x,pos.y,pos.body,pos.fresh = cur.x,cur.y,bodytable[tablepos][1],bodytable[tablepos][2]
  3217.                     end
  3218.                 end
  3219.                 if pos.x then break end
  3220.                 if j ~= a and j ~= -a then
  3221.                     i = i+a*2
  3222.                 else
  3223.                     i = i+1
  3224.                 end
  3225.             end
  3226.             if pos.x then break end
  3227.             j = j+1
  3228.         end
  3229.         if pos.x then break end
  3230.     end
  3231.     if pos.x then
  3232.         pausewalking(20000)
  3233.         reachlocation(pos.x,pos.y,pos.z)
  3234.         local topid = topitem(pos.x,pos.y,pos.z).id
  3235.         while topid ~= pos.fresh and topid ~= pos.body and not iscreatureontile(pos.x, pos.y, pos.z) and not itemproperty(topid, ITEM_NOTMOVEABLE) do
  3236.             local dir, dirx, diry = wheretomoveitem(pos.x,pos.y,pos.z,topid)
  3237.             moveitems(topid, ground(pos.x+dirx,pos.y+diry,pos.z), ground(pos.x,pos.y,pos.z), 100) waitping()
  3238.             topid = topitem(pos.x,pos.y,pos.z).id
  3239.         end
  3240.         while topid == pos.fresh do wait(500) topid = topitem(pos.x,pos.y,pos.z).id end
  3241.        
  3242.         useitemon(touseid, pos.body, ground(pos.x,pos.y,pos.z), itempos) waitping(1.4, 1.7)
  3243.         pausewalking(0)
  3244.         return true
  3245.     end
  3246.     return false
  3247. end
  3248.  
  3249. function skin(dist, movebody, waitfresh)
  3250.     if type(movebody) ~= 'boolean' then
  3251.         movebody = false
  3252.     end
  3253.     if type(waitfresh) ~= 'boolean' then
  3254.         waitfresh = false
  3255.     end
  3256.     return skinsample(dist, movebody, waitfresh, 5908, SKINLIST)
  3257. end
  3258.  
  3259. function stake(dist, movebody, waitfresh)
  3260.     if type(movebody) ~= 'boolean' then
  3261.         movebody = false
  3262.     end
  3263.     if type(waitfresh) ~= 'boolean' then
  3264.         waitfresh = false
  3265.     end
  3266.     return skinsample(dist, movebody, waitfresh, 5942, STAKELIST)
  3267. end
  3268.  
  3269. function skinkitchenknife(dist, movebody, waitfresh)
  3270.     if type(movebody) ~= 'boolean' then
  3271.         movebody = false
  3272.     end
  3273.     if type(waitfresh) ~= 'boolean' then
  3274.         waitfresh = false
  3275.     end
  3276.     return skinsample(dist, movebody, waitfresh, 3469, {{4173, 6017, 'rabbit'}})
  3277. end
  3278.  
  3279. FISHSPOTS = {time = 0, id = 0, nonfish = {}, fish = {}}
  3280. function FISHSPOTS:update(id)
  3281.     self.time = $timems
  3282.     self.id = id
  3283.     self.nonfish = {}
  3284.     self.fish = {}
  3285.     for j=-5,5 do
  3286.         for i=-7,7 do
  3287.             local cur = {x=$posx+i,y=$posy+j,z=$posz,id=0}
  3288.             cur.id = topitem(cur.x,cur.y,cur.z).id
  3289.             if tileshootable(cur.x,cur.y,cur.z) then
  3290.                 if self.id <= 100 and self.id >= 0 then
  3291.                     if cur.id >= 4597 and cur.id <= 4602 then
  3292.                         table.insert(self.fish, {x=cur.x,y=cur.y,z=cur.z})
  3293.                     elseif cur.id >= 4609 and cur.id <= 4614 then
  3294.                         table.insert(self.nonfish, {x=cur.x,y=cur.y,z=cur.z})
  3295.                     end
  3296.                 elseif (type(self.id) == 'number' and self.id == cur.id) or table.find(self.id,cur.id) then
  3297.                     local tile = gettile(cur.x,cur.y,cur.z)
  3298.                     local insert = true
  3299.                     for k=1, tile.itemcount do
  3300.                         local tempid = tile.item[k].id
  3301.                         if tempid == 99 or table.find(stairsids,tempid) then
  3302.                             insert = false
  3303.                             break
  3304.                         end
  3305.                     end
  3306.                     if insert then
  3307.                         table.insert(self.fish, {x=cur.x,y=cur.y,z=cur.z})
  3308.                     end
  3309.                 end
  3310.             end
  3311.         end
  3312.     end
  3313. end
  3314.  
  3315. function FISHSPOTS:clear()
  3316.     self.time = 0
  3317.     self.id = 0
  3318.     self.nonfish = {}
  3319.     self.fish = {}
  3320. end
  3321.  
  3322. function comparetables(a,b)
  3323.     if #a ~= #b then
  3324.         return false
  3325.     end
  3326.     for i,j in ipairs(a) do
  3327.         if j ~= b[i] then
  3328.             return false
  3329.         end
  3330.     end
  3331.     for i,j in pairs(a) do
  3332.         if j ~= b[i] then
  3333.             return false
  3334.         end
  3335.     end
  3336.     return true
  3337. end
  3338.  
  3339. function fish(n)
  3340.     n = n or 0
  3341.     local rodid,rodpos = 3483
  3342.     if clientitemhotkey(rodid,'crosshair') == 'not found' then
  3343.         rodpos = ''
  3344.     end
  3345.     if $timems-FISHSPOTS.time > 100 or (type(n) == 'number' and n ~= FISHSPOTS.id) or (type(n) == 'table' and not comparetables(n, FISHSPOTS.id)) then
  3346.         FISHSPOTS:update(n)
  3347.     end
  3348.     local j = math.random(1,100)
  3349.     local tofish
  3350.     if (#FISHSPOTS.nonfish > 0 and n <= 100) and (j <= n or #FISHSPOTS.fish == 0) then
  3351.         j = math.random(1,#FISHSPOTS.nonfish)
  3352.         tofish = FISHSPOTS.nonfish[j]
  3353.     elseif #FISHSPOTS.fish > 0 and (#FISHSPOTS.nonfish == 0 or n == 0 or n > 100 or j > n) then
  3354.         j = math.random(1,#FISHSPOTS.fish)
  3355.         tofish = FISHSPOTS.fish[j]
  3356.     end
  3357.     if tofish then
  3358.         pausewalking(10000)
  3359.         useitemon(rodid,topitem(tofish.x,tofish.y,tofish.z).id,ground(tofish.x,tofish.y,tofish.z),rodpos) waitping(1.1,1.4)
  3360.         pausewalking(0)
  3361.     end
  3362. end
  3363.  
  3364. function fishspots(n)
  3365.     n = n or 0
  3366.     if $timems-FISHSPOTS.time > 100 or (type(n) == 'number' and n ~= FISHSPOTS.id) or (type(n) == 'table' and not comparetables(n, FISHSPOTS.id)) then
  3367.         FISHSPOTS:update(n)
  3368.     end
  3369.     return #FISHSPOTS.fish
  3370. end
  3371.  
  3372. function settargeting(onoff, stopattacking, t)
  3373.     if (onoff == nil) then
  3374.         return
  3375.     else
  3376.         onoff = onoff:lower()
  3377.         if (onoff == 'on') or (onoff == 'yes') then
  3378.             onoff = 'yes'
  3379.         elseif (onoff == 'off') or (onoff == 'no') then
  3380.             onoff = 'no'
  3381.         end
  3382.     end
  3383.     setsetting('Targeting/TargetingEnabled', onoff, t)
  3384.     if onoff == 'no' and stopattacking ~= false then
  3385.         stopattack()
  3386.     end
  3387. end
  3388.  
  3389. function setcavebot(onoff, t)
  3390.     if (onoff == nil) then
  3391.         return
  3392.     else
  3393.         onoff = onoff:lower()
  3394.         if (onoff == 'on') or (onoff == 'yes') then
  3395.             onoff = 'yes'
  3396.         elseif (onoff == 'off') or (onoff == 'no') then
  3397.             onoff = 'no'
  3398.         end
  3399.     end
  3400.     setsetting('Cavebot/CavebotEnabled', onoff, t)
  3401. end
  3402.  
  3403. function setlooting(onoff, t)
  3404.     if (onoff == nil) then
  3405.         return
  3406.     else
  3407.         onoff = onoff:lower()
  3408.         if (onoff == 'on') or (onoff == 'yes') then
  3409.             onoff = 'yes'
  3410.         elseif (onoff == 'off') or (onoff == 'no') then
  3411.             onoff = 'no'
  3412.         end
  3413.     end
  3414.     setsetting('Cavebot/Looting/LootingEnabled', onoff, t)
  3415. end
  3416.  
  3417. function sethealing(onoff, t)
  3418.     if (onoff == nil) then
  3419.         return
  3420.     else
  3421.         onoff = onoff:lower()
  3422.         if (onoff == 'on') or (onoff == 'yes') then
  3423.             onoff = 'yes'
  3424.         elseif (onoff == 'off') or (onoff == 'no') then
  3425.             onoff = 'no'
  3426.         end
  3427.     end
  3428.     setsetting('Healer/HealerEnabled', onoff, t)
  3429. end
  3430.  
  3431. function setmanatraining(onoff, t)
  3432.     if (onoff == nil) then
  3433.         return
  3434.     else
  3435.         onoff = onoff:lower()
  3436.         if (onoff == 'on') or (onoff == 'yes') then
  3437.             onoff = 'yes'
  3438.         elseif (onoff == 'off') or (onoff == 'no') then
  3439.             onoff = 'no'
  3440.         end
  3441.     end
  3442.     setsetting('Healer/ManaTraining/Enabled', onoff, t)
  3443. end
  3444.  
  3445. function setalarm(alarmtype, playsound, pausebot, logout, t)
  3446.     local alarmtypes = {'PlayerOnScreen','PlayerAttacking','DefaultMessage','PrivateMessage','GmDetected','Disconnected','CrashedFroze'}
  3447.     local alarmtypes2 = {'playeronscreen','playerattacking','defaultmessage','privatemessage','gmdetected','disconnected','crashedfroze'}
  3448.     local pos = table.find(alarmtypes2,alarmtype:lower())
  3449.     if not pos then
  3450.         return
  3451.     end
  3452.     if not playsound or playsound == 'off' or playsound == 'no' or playsound == 0 then
  3453.         playsound = 'no'
  3454.     elseif playsound == 'on' or playsound == 'yes' or playsound == 1 then
  3455.         playsound = 'yes'
  3456.     end
  3457.     if not pausebot or pausebot == 'off' or pausebot == 'no' or pausebot == 0 then
  3458.         pausebot = 'no'
  3459.     elseif pausebot == 'on' or pausebot == 'yes' or pausebot == 1 then
  3460.         pausebot = 'yes'
  3461.     end
  3462.     if not logout or logout == 'off' or logout == 'no' or logout == 0 then
  3463.         logout = 'no'
  3464.     elseif logout == 'on' or logout == 'yes' or logout == 1 then
  3465.         logout = 'yes'
  3466.     end
  3467.     setsetting('Alerts/'..alarmtypes[pos]..'/PlaySound', playsound, t)
  3468.     setsetting('Alerts/'..alarmtypes[pos]..'/FlashClient', playsound, t)
  3469.     setsetting('Alerts/'..alarmtypes[pos]..'/PauseBot', pausebot, t)
  3470.     setsetting('Alerts/'..alarmtypes[pos]..'/Disconnect', logout, t)
  3471. end
  3472.  
  3473. function addtosafelist(safetype, ...)
  3474.     local alarmtypes = {'PlayerOnScreen','PlayerAttacking','DefaultMessage','PrivateMessage','GmDetected','Disconnected','CrashedFroze'}
  3475.     local alarmtypes2 = {'playeronscreen','playerattacking','defaultmessage','privatemessage','gmdetected','disconnected','crashedfroze'}
  3476.     local pos = table.find(alarmtypes2,alarmtype:lower())
  3477.     if not pos then return end
  3478.     local cursafe = getsetting('Alerts/'..alarmtypes[pos]..'/SafeList'):token(nil,'\n')
  3479.     table.lower(cursafe)
  3480.     for i,j in ipairs({...}) do
  3481.         if not table.find(cursafe,j:lower()) then
  3482.             table.insert(cursafe,j)
  3483.         end
  3484.     end
  3485.     local p = ''
  3486.     for i,j in ipairs(cursafe) do
  3487.         p = p..j..'\n'
  3488.     end
  3489.     setsetting('Alerts/'..alarmtypes[pos]..'/SafeList',p)
  3490. end
  3491.  
  3492. function removefromsafelist(safetype, ...)
  3493.     local alarmtypes = {'PlayerOnScreen','PlayerAttacking','DefaultMessage','PrivateMessage','GmDetected','Disconnected','CrashedFroze'}
  3494.     local alarmtypes2 = {'playeronscreen','playerattacking','defaultmessage','privatemessage','gmdetected','disconnected','crashedfroze'}
  3495.     local pos = table.find(alarmtypes2,alarmtype:lower())
  3496.     if not pos then return end
  3497.     local cursafe = getsetting('Alerts/'..alarmtypes[pos]..'/SafeList'):token(nil,'\n')
  3498.     table.lower(cursafe)
  3499.     for i,j in ipairs({...}) do
  3500.         local m = table.find(cursafe,j:lower())
  3501.         if m then
  3502.             table.remove(cursafe,m)
  3503.         end
  3504.     end
  3505.     local p = ''
  3506.     for i,j in ipairs(cursafe) do
  3507.         p = p..j..'\n'
  3508.     end
  3509.     setsetting('Alerts/'..alarmtypes[pos]..'/SafeList',p)
  3510. end
  3511.  
  3512. function stopattack()
  3513.     keyevent(0x1B)
  3514. end
  3515.  
  3516. function string:token(n,delimiter)
  3517.     delimiter = delimiter or ' +'
  3518.     local result = {}
  3519.     local from = 1
  3520.     local delim_from, delim_to = self:find(delimiter,from)
  3521.     while delim_from do
  3522.         table.insert(result, self:sub(from,delim_from-1))
  3523.         from = delim_to + 1
  3524.         delim_from, delim_to = self:find(delimiter,from)
  3525.     end
  3526.     table.insert(result,self:sub(from))
  3527.     if n then
  3528.         return result[n]
  3529.     end
  3530.     return result
  3531. end
  3532.  
  3533. function string:fitcontent(size,margin,fontsize)
  3534.     local maxletters = math.floor((size-2*(margin+3))/(fontsize-1.5))
  3535.     if self:len() > maxletters then
  3536.         return self:sub(1,maxletters)..'...'
  3537.     end
  3538.     return self
  3539. end
  3540.  
  3541. local spellsareas = {
  3542. sstrike = {centerx = 2, centery = 2, area = {
  3543.                 {0,2,0},
  3544.                 {3,0,4},
  3545.                 {0,5,0}}},
  3546. ssmallwave = {centerx = 5, centery = 5, area = {
  3547.                 {0,0,2,2,2,2,2,0,0},
  3548.                 {0,0,0,2,2,2,0,0,0},
  3549.                 {3,0,0,2,2,2,0,0,4},
  3550.                 {3,3,3,0,2,0,4,4,4},
  3551.                 {3,3,3,3,0,4,4,4,4},
  3552.                 {3,3,3,0,5,0,4,4,4},
  3553.                 {3,0,0,5,5,5,0,0,4},
  3554.                 {0,0,0,5,5,5,0,0,0},
  3555.                 {0,0,5,5,5,5,5,0,0}}},
  3556. sbigwave = {centerx = 6, centery = 6, area = {
  3557.                 {0,0,0,0,2,2,2,0,0,0,0},
  3558.                 {0,0,0,0,2,2,2,0,0,0,0},
  3559.                 {0,0,0,0,2,2,2,0,0,0,0},
  3560.                 {0,0,0,0,0,2,0,0,0,0,0},
  3561.                 {3,3,3,0,0,2,0,0,4,4,4},
  3562.                 {3,3,3,3,3,0,4,4,4,4,4},
  3563.                 {3,3,3,0,0,5,0,0,4,4,4},
  3564.                 {0,0,0,0,0,5,0,0,0,0,0},
  3565.                 {0,0,0,0,5,5,5,0,0,0,0},
  3566.                 {0,0,0,0,5,5,5,0,0,0,0},
  3567.                 {0,0,0,0,5,5,5,0,0,0,0}}},
  3568. ssmallbeam = {centerx = 6, centery = 6, area = {
  3569.                 {0,0,0,0,0,2,0,0,0,0,0},
  3570.                 {0,0,0,0,0,2,0,0,0,0,0},
  3571.                 {0,0,0,0,0,2,0,0,0,0,0},
  3572.                 {0,0,0,0,0,2,0,0,0,0,0},
  3573.                 {0,0,0,0,0,2,0,0,0,0,0},
  3574.                 {3,3,3,3,3,0,4,4,4,4,4},
  3575.                 {0,0,0,0,0,5,0,0,0,0,0},
  3576.                 {0,0,0,0,0,5,0,0,0,0,0},
  3577.                 {0,0,0,0,0,5,0,0,0,0,0},
  3578.                 {0,0,0,0,0,5,0,0,0,0,0},
  3579.                 {0,0,0,0,0,5,0,0,0,0,0}}},
  3580. sbigbeam = {centerx = 9, centery = 9, area = {
  3581.                 {0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0},
  3582.                 {0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0},
  3583.                 {0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0},
  3584.                 {0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0},
  3585.                 {0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0},
  3586.                 {0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0},
  3587.                 {0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0},
  3588.                 {0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0},
  3589.                 {3,3,3,3,3,3,3,3,0,4,4,4,4,4,4,4,4},
  3590.                 {0,0,0,0,0,0,0,0,5,0,0,0,0,0,0,0,0},
  3591.                 {0,0,0,0,0,0,0,0,5,0,0,0,0,0,0,0,0},
  3592.                 {0,0,0,0,0,0,0,0,5,0,0,0,0,0,0,0,0},
  3593.                 {0,0,0,0,0,0,0,0,5,0,0,0,0,0,0,0,0},
  3594.                 {0,0,0,0,0,0,0,0,5,0,0,0,0,0,0,0,0},
  3595.                 {0,0,0,0,0,0,0,0,5,0,0,0,0,0,0,0,0},
  3596.                 {0,0,0,0,0,0,0,0,5,0,0,0,0,0,0,0,0},
  3597.                 {0,0,0,0,0,0,0,0,5,0,0,0,0,0,0,0,0}}},
  3598. sfront = {centerx = 2, centery = 2, area = {
  3599.                 {9,2,6},
  3600.                 {3,0,4},
  3601.                 {8,5,7}}},
  3602. sexplo = {centerx = 2, centery = 2, area = {
  3603.                 {0,1,0},
  3604.                 {1,1,1},
  3605.                 {0,1,0}}},
  3606. s1x1 = {centerx = 2, centery = 2, area = {
  3607.                 {1,1,1},
  3608.                 {1,1,1},
  3609.                 {1,1,1}}},
  3610. s2x2 = {centerx = 3, centery = 3, area = {
  3611.                 {0,1,1,1,0},
  3612.                 {1,1,1,1,1},
  3613.                 {1,1,1,1,1},
  3614.                 {1,1,1,1,1},
  3615.                 {0,1,1,1,0}}},
  3616. s3x3 = {centerx = 4, centery = 4, area = {
  3617.                 {0,0,1,1,1,0,0},
  3618.                 {0,1,1,1,1,1,0},
  3619.                 {1,1,1,1,1,1,1},
  3620.                 {1,1,1,1,1,1,1},
  3621.                 {1,1,1,1,1,1,1},
  3622.                 {0,1,1,1,1,1,0},
  3623.                 {0,0,1,1,1,0,0}}},
  3624. s5x5 = {centerx = 6, centery = 6, area = {
  3625.                 {0,0,0,0,0,1,0,0,0,0,0},
  3626.                 {0,0,0,1,1,1,1,1,0,0,0},
  3627.                 {0,0,1,1,1,1,1,1,1,0,0},
  3628.                 {0,1,1,1,1,1,1,1,1,1,0},
  3629.                 {0,1,1,1,1,1,1,1,1,1,0},
  3630.                 {1,1,1,1,1,1,1,1,1,1,1},
  3631.                 {0,1,1,1,1,1,1,1,1,1,0},
  3632.                 {0,1,1,1,1,1,1,1,1,1,0},
  3633.                 {0,0,1,1,1,1,1,1,1,0,0},
  3634.                 {0,0,0,1,1,1,1,1,0,0,0},
  3635.                 {0,0,0,0,0,1,0,0,0,0,0}}},
  3636. s6x6 = {centerx = 7, centery = 7, area = {
  3637.                 {0,0,0,0,0,0,1,0,0,0,0,0,0},
  3638.                 {0,0,0,0,1,1,1,1,1,0,0,0,0},
  3639.                 {0,0,0,1,1,1,1,1,1,1,0,0,0},
  3640.                 {0,0,1,1,1,1,1,1,1,1,1,0,0},
  3641.                 {0,1,1,1,1,1,1,1,1,1,1,1,0},
  3642.                 {0,1,1,1,1,1,1,1,1,1,1,1,0},
  3643.                 {1,1,1,1,1,1,1,1,1,1,1,1,1},
  3644.                 {0,1,1,1,1,1,1,1,1,1,1,1,0},
  3645.                 {0,1,1,1,1,1,1,1,1,1,1,1,0},
  3646.                 {0,0,1,1,1,1,1,1,1,1,1,0,0},
  3647.                 {0,0,0,1,1,1,1,1,1,1,0,0,0},
  3648.                 {0,0,0,0,1,1,1,1,1,0,0,0,0},
  3649.                 {0,0,0,0,0,0,1,0,0,0,0,0,0}}}}
  3650.  
  3651. function isonspellarea(mid,spelltype,spelldir,x,y)
  3652.     if not spelldir then
  3653.         spelldir = $self.dir
  3654.     end
  3655.     local directionconversion = {nil, $self.dir, 'n', 'w', 'e', 's', 'ne', 'se', 'sw', 'nw'}
  3656.     mid = findcreature(mid)
  3657.     if mid.id == 0 then
  3658.         return false
  3659.     end
  3660.     local numberspelltype = tonumber(spelltype)
  3661.     if type(spelltype) == 'string' then
  3662.         spelltype = 's'..(spelltype:gsub(' ','')):lower()
  3663.     else
  3664.         return false
  3665.     end
  3666.     if not (x and y) then
  3667.         x,y = $posx,$posy
  3668.     elseif math.abs(x) <= 7 and math.abs(y) <= 5 then
  3669.         x,y = $posx+x,$posy+y
  3670.     else
  3671.         x,y = nil,nil
  3672.     end
  3673.    
  3674.     if mid and (spellsareas[spelltype] or numberspelltype) and mid.posz == $posz and x and y and mid.isshootable then
  3675.         if numberspelltype then
  3676.             if mid == $attacked and mid.dist <= numberspelltype then
  3677.                 return true
  3678.             else
  3679.                 return false
  3680.             end
  3681.         end
  3682.         local centerx,centery = spellsareas[spelltype].centerx,spellsareas[spelltype].centery
  3683.         local posx,posy = centerx-(x-mid.posx),centery-(y-mid.posy)
  3684.         local value
  3685.         if posx >= 1 and posx <= centerx*2-1 and posy >= 1 and posy <= centery*2-1 then
  3686.             value = directionconversion[spellsareas[spelltype].area[posy][posx]+1]
  3687.         end
  3688.         if value and (value:find(spelldir) or spelldir == 'any') then
  3689.             return true
  3690.         end
  3691.     end
  3692.     return false
  3693. end
  3694.  
  3695. function wheretoturn(mid,spelltype)
  3696.     local directionconversion = {nil, $self.dir, 'n', 'w', 'e', 's', 'ne', 'se', 'sw', 'nw'}
  3697.     if type(mid) == 'number' or type(mid) == 'string' then
  3698.         mid = findcreature(mid)
  3699.     end
  3700.     local numberspelltype = tonumber(spelltype)
  3701.     if numberspelltype then
  3702.         spelltype = numberspelltype
  3703.     elseif type(spelltype) == 'string' then
  3704.         spelltype = 's'..(spelltype:gsub(' ','')):lower()
  3705.     else
  3706.         return $self.dir
  3707.     end
  3708.     local x,y = $posx,$posy
  3709.     if mid and mid.id ~= 0 and mid.posz == $posz and x and y and mid.isshootable then
  3710.         local centerx,centery = spellsareas[spelltype].centerx,spellsareas[spelltype].centery
  3711.         local posx,posy = centerx-(x-mid.posx),centery-(y-mid.posy)
  3712.         local value = $self.dir
  3713.         if posx >= 1 and posx <= centerx*2-1 and posy >= 1 and posy <= centery*2-1 then
  3714.             value = directionconversion[spellsareas[spelltype].area[posy][posx] +1]
  3715.         end
  3716.         if value:find($self.dir) then
  3717.             return $self.dir
  3718.         end
  3719.         local rand = math.random(1,#value)
  3720.         return value:sub(rand,rand)
  3721.     end
  3722.     return $self.dir
  3723. end
  3724.  
  3725. function getarearunetile(ignoreplayers,...)
  3726.     monsters = {...}
  3727.     table.lower(monsters)
  3728.     local sqm = {tile,x,y,z,amount=0}
  3729.     for a=0,7 do
  3730.         local i,j = -a, -a
  3731.         while j <= a do
  3732.             i = -a
  3733.             while i <= a do
  3734.                 if (math.abs(j) == a or math.abs(i) == a) and (tilehasinfo($posx+i, $posy+j, $posz)) then
  3735.                     local posx,posy = $posx+i,$posy+j
  3736.                     if tileshootable(posx,posy,$posz) then
  3737.                         local tempm,tempp = 0,0
  3738.                         foreach creature c 'f' do
  3739.                             if c ~= $self then
  3740.                                 if isonspellarea(c, '3x3', false, i, j) then
  3741.                                     if (#monsters == 0 and (c.ismonster or ignoreplayers)) or table.find(monsters,c.name:lower()) or table.find(monsters,c.id) or table.find(monsters,c) then
  3742.                                         tempm = tempm+1
  3743.                                     elseif c.isplayer then
  3744.                                         tempp = tempp+1
  3745.                                     end
  3746.                                 end
  3747.                             end
  3748.                             if tempm > sqm.amount and (ignoreplayers or tempp == 0) then
  3749.                                 sqm.tile,sqm.x,sqm.y,sqm.z,sqm.amount = ground(posx,posy,$posz),posx,posy,$posz,tempm
  3750.                             end
  3751.                         end
  3752.                     end
  3753.                 end
  3754.                 if math.abs(j) ~= a then
  3755.                     i = i+2*a
  3756.                 else
  3757.                     i = i+1
  3758.                 end
  3759.             end
  3760.             j = j+1
  3761.         end
  3762.     end
  3763.     return sqm
  3764. end
  3765.  
  3766. function shootarearune(id, amount, ignoreplayers, ...)
  3767.     id = itemid(id)
  3768.     local monsters = {...}
  3769.     if ignoreplayers then
  3770.         if type(ignoreplayers) == 'string' or (type(ignoreplayers) == 'number' and ignoreplayers > 100) then
  3771.             table.insert(monsters,ignoreplayers)
  3772.         end
  3773.         ignoreplayers = ignoreplayers == true or false
  3774.     end
  3775.     if amount then
  3776.         if type(amount) == 'string' or (type(amount) == 'number' and amount > 100) then
  3777.             table.insert(monsters,amount)
  3778.             amount = 1
  3779.         end
  3780.     end
  3781.     amount = amount or 1
  3782.     local temp = getarearunetile(ignoreplayers, table.unpack(monsters))
  3783.     if temp.amount >= amount then
  3784.         useitemon(id, topitem(temp.x,temp.y,temp.z), temp.tile)
  3785.         return true
  3786.     end
  3787.     return false
  3788. end
  3789.  
  3790. function cursorinfo() -- Credits to Anonymickey, for doing the calculations.
  3791.     local temp = {x,y,z,id,msg}
  3792.     if $cursor.x >= $worldwin.left and $cursor.x <= $worldwin.right and $cursor.y <= $worldwin.bottom and $cursor.y >= $worldwin.top then
  3793.         local sqmWidth = ($worldwin.bottom - $worldwin.top)/11
  3794.         temp.x, temp.y, temp.z =  $posx - 8 + math.ceil(($cursor.x - $worldwin.left)/sqmWidth), $posy - 6 + math.ceil(($cursor.y - $worldwin.top)/sqmWidth), $posz
  3795.         temp.id = topitem(temp.x, temp.y, temp.z).id
  3796.         temp.msg = temp.x..', '..temp.y..', '..temp.z..' / '..temp.id
  3797.     else
  3798.         temp.x, temp.y, temp.z, temp.id, temp.msg = 0,0,0,0,'dontlist'
  3799.     end
  3800.     return temp
  3801. end
  3802.  
  3803. function tobin(x, reverse)
  3804.     local bin = ''
  3805.     while x ~= 0 do
  3806.         local mod = x % 2
  3807.         if reverse then
  3808.             bin = bin .. mod
  3809.         else
  3810.             bin = mod .. bin
  3811.         end
  3812.         x = math.floor(x/2)
  3813.     end
  3814.     return bin
  3815. end
  3816.  
  3817. function bintonum(x)
  3818.     if type(x) == 'number' then
  3819.         x = tostring(x)
  3820.     elseif type(x) ~= 'string' then
  3821.         return
  3822.     end
  3823.     local num = 0
  3824.     for i=1,x:len() do
  3825.         num = num*2 + tonumber(x:sub(i,i))
  3826.     end
  3827.     return num
  3828. end
  3829.  
  3830. function table:lower(inpairs)
  3831.     if not inpairs then
  3832.         for i,j in ipairs(self) do
  3833.             if type(j) == 'string' then
  3834.                 self[i] = j:lower()
  3835.             end
  3836.         end
  3837.     else
  3838.         for i,j in pairs(self) do
  3839.             if type(j) == 'string' then
  3840.                 self[i] = j:lower()
  3841.             end
  3842.         end
  3843.     end
  3844. end
  3845.  
  3846. function table:id(inpairs)
  3847.     if not inpairs then
  3848.         local i = 1
  3849.         while i <= #self do
  3850.             if type(self[i]) == 'string' then
  3851.                 local iid = itemid(self[i])
  3852.                 if iid ~= 0 then
  3853.                     self[i] = iid
  3854.                     i = i+1
  3855.                 else
  3856.                     table.remove(self,i)
  3857.                 end
  3858.             elseif type(self[i]) == 'number' then
  3859.                 i = i+1
  3860.             else
  3861.                 table.remove(self,i)
  3862.             end
  3863.         end
  3864.     else
  3865.         for i,j in pairs(self) do
  3866.             if type(j) == 'string' then
  3867.                 self[i] = itemid(j)
  3868.             end
  3869.         end
  3870.     end
  3871. end
  3872.  
  3873. function table:spell(inpairs)
  3874.     if not inpairs then
  3875.         local i = 1
  3876.         while i <= #self do
  3877.             if type(self[i]) == 'string' then
  3878.                 local iid = spellinfo(self[i])
  3879.                 if iid then
  3880.                     self[i] = iid
  3881.                     i = i+1
  3882.                 else
  3883.                     table.remove(self,i)
  3884.                 end
  3885.             elseif type(self[i]) == 'table' then
  3886.                 i = i+1
  3887.             else
  3888.                 table.remove(self,i)
  3889.             end
  3890.         end
  3891.     else
  3892.         for i,j in pairs(self) do
  3893.             if type(j) == 'string' then
  3894.                 local tsinfo = spellinfo(j)
  3895.                 if tsinfo then
  3896.                     self[i] = tsinfo
  3897.                 else
  3898.                     table.remove(self,i)
  3899.                 end
  3900.             end
  3901.         end
  3902.     end
  3903. end
  3904.  
  3905. function table:upper(inpairs)
  3906.     if not inpairs then
  3907.         for i,j in ipairs(self) do
  3908.             if type(j) == 'string' then
  3909.                 self[i] = j:upper()
  3910.             end
  3911.         end
  3912.     else
  3913.         for i,j in pairs(self) do
  3914.             if type(j) == 'string' then
  3915.                 self[i] = j:upper()
  3916.             end
  3917.         end
  3918.     end
  3919. end
  3920.  
  3921. function foodcount()
  3922.     temp = 0
  3923.     for i,j in ipairs(eatfoodids) do
  3924.         temp = temp+itemcount(j)
  3925.     end
  3926.     return temp
  3927. end
  3928.  
  3929. function isfood(id)
  3930.     id = itemid(id)
  3931.     return table.binaryfind(eatfoodids,id) ~= nil
  3932. end
  3933.  
  3934. local travelnpcs = {{'Anderson', {folda = {32046,31580,7}, vega = {32022,31692,7}, tibia = {32234,31675,7}}},
  3935.                     {'Carlson', {folda = {32046,31580,7}, senja = {32126,31665,7}, tibia = {32234,31675,7}}},
  3936.                     {'Svenson', {vega = {32022,31692,7}, senja = {32126,31665,7}, tibia = {32234,31675,7}}},
  3937.                     {'Nielson', {folda = {32046,31580,7}, senja = {32126,31665,7}, vega = {32022,31692,7}}},
  3938.                     {'Chemar', {edron = {33193,31784,3}, farmine = {32983,31539,1}, hills = {32535,31837,4}, svargrond = {32254,31097,4}}},
  3939.                     {'Iyad', {edron = {33193,31784,3}, hills = {32535,31837,4}, darashia = {33269,32441,6}, farmine = {32983,31539,1}}},
  3940.                     {'Pino', {darashia = {33269,32441,6}, svargrond = {32254,31097,4}, farmine = {32983,31539,1}, hills = {32535,31837,4}}},
  3941.                     {'Uzon', {darashia = {33269,32441,6}, farmine = {32983,31539,1}, svargrond = {32254,31097,4}, edron = {33193,31784,3}--[[, eclipse = nil--]]}},
  3942.                     {'Melian', {darashia = {33269,32441,6}, edron = {33193,31784,3}, hills = {32535,31837,4}, svargrond = {32254,31097,4}}},
  3943.                     {'Brodrosch', {cormaya = {33309,31989,15}, farmine = {33024,31552,10}}},
  3944.                     {'Thorgrin', {cormaya = {33309,31989,15}, kazordoon = {33309,31989,15}}},                  
  3945.                     {'Captain Bluebear', {abdendriel = {32733,31668,6}, carlin = {32387,31821,6}, edron = {33193,31784,3}, libertybay = {32283,32893,6}, porthope = {32530,32784,6}, svargrond = {32341,31108,6}, venore = {32954,32023,6}, yalahar = {32816,31272,6}}},
  3946.                     {'Captain Breezelda', {venore = {32954,32023,6}, thais = {32312,32211,6}, carlin = {32387,31821,6}}},
  3947.                     {'Captain Cookie', {libertybay = {32298,32896,6}}},
  3948.                     {'Captain Fearless', {abdendriel = {32733,31668,6}, carlin = {32387,31821,6}, edron = {33175,31764,6}, darashia = {33289,32480,6}, thais = {32312,32211,6}, porthope = {32530,32784,6}, ankrahmun = {33091,32883,6}, libertybay = {32283,32893,6}, svargrond = {32341,31108,6}, yalahar = {32816,31272,6}}},
  3949.                     {'Captain Greyhound', {abdendriel = {32733,31668,6}, edron = {33175,31764,6}, svargrond = {32341,31108,6}, thais = {32312,32211,6}, venore = {32954,32023,6}, yalahar = {32816,31272,6}}},
  3950.                     {'Captain Seagull', {carlin = {32387,31821,6}, edron = {33175,31764,6}, thais = {32312,32211,6}, venore = {32954,32023,6}, yalahar = {32816,31272,6}}},
  3951.                     {'Captain Seahorse', {abdendriel = {32733,31668,6}, ankrahmun = {33091,32883,6}, carlin = {32387,31821,6}, cormaya = {33288,31956,6}, libertybay = {32283,32893,6}, porthope = {32530,32784,6}, thais = {32312,32211,6}, venore = {32954,32023,6}}},
  3952.                     {'Captain Sinbeard', {darashia = {33289,32480,6}, venore = {32954,32023,6}, libertybay = {32283,32893,6}, porthope = {32530,32784,6}, edron = {33175,31764,6}, yalahar = {32816,31272,6}}},
  3953.                     {'Charles', {ankrahmun = {33091,32883,6}, darashia = {33289,32480,6}, edron = {33175,31764,6}, thais = {32312,32211,6}, venore = {32954,32023,6}, libertybay = {32283,32893,6}, yalahar = {32816,31272,6}}},
  3954.                     {'Jack Fate', {ankrahmun = {33091,32883,6}, darashia = {33289,32480,6}, edron = {33175,31764,6}, porthope = {32530,32784,6}, thais = {32312,32211,6}, venore = {32954,32023,6}, yalahar = {32816,31272,6}, goroma = {32161,32558,6}, libertybay = {32283,32893,6}}},
  3955.                     {'Karith', {abdendriel = {32733,31668,6}, darashia = {33289,32480,6}, venore = {32954,32023,6}, ankrahmun = {33091,32883,6}, porthope = {32530,32784,6}, thais = {32312,32211,6}, libertybay = {32283,32893,6}, carlin = {32387,31821,6}}},
  3956.                     {'Petros', {ankrahmun = {33091,32883,6}, venore = {32954,32023,6}, porthope = {32530,32784,6}, libertybay = {32283,32893,6}, yalahar = {32816,31272,6}}},
  3957.                     {'Captain Haba', {hunt = {31942,31047,6}, svargrond = {32339,31117,7}}},
  3958.                     {'Captain Jack', {tibia = {32205,31756,6}}},
  3959.                     {'Captain Max', {calassa = {31920,32710,7}, libertybay = {32298,32896,6}, yalahar = {32804,31270,6}}},
  3960.                     {'Captain Waverider', {pegleg = {32346,32625,7}, libertybay = {32350,32856,7}, passage = {32132,32912,7}}},
  3961.                     {'Dalbrect', {passage = {32190,31957,6}}},
  3962.                     {'Gurbasch', {kazordoon = {33309,31989,15}, farmine = {33024,31552,10}}},
  3963.                     {'Harlow', {vengoth = {32857,31549,7}, yalahar = {32837,31364,7}}},
  3964.                     {'Maris', {mistrock = {32640,31439,7}, fenrock = {32564,31313,7}, yalahar = {32649,31292,6}}},
  3965.                     {'Pemaret', {edron = {33175,31764,6}, eremo = {33315,31882,7}}},
  3966.                     {'Eremo', {cormaya = {33288,31956,6}}},
  3967.                     {'Sebastian', {nargor = {32025,32812,7}, libertybay = {32316,32702,7}, meriana = {32346,32625,7}}},
  3968.                     {'Buddel', {okolnir = {32224,31381,7}, camp = {32153,31376,7}, tyrsung = {32333,31227,7}, helheim = {32462,31174,7}, svargrond = {32256,31197,7}}},
  3969.                     {'Rapanaio', {kazordoon = {32700,31989,15}, isleofevil = {32667,31452,7}}},
  3970.                     {'Imbul', {east = {32679,32777,7}, center = {32628,32771,7}--[[, mountain = --]], chor = {32968,32799,7}--[[, banuta--]]}},
  3971.                     {'Old Adall', {east = {32679,32777,7}, west = {32558,32780,7}--[[, mountain = --]], chor = {32968,32799,7}--[[, banuta--]]}},
  3972.                     {'Lorek', {center = {32628,32771,7}, west = {32558,32780,7}--[[, mountain = --]], chor = {32968,32799,7}--[[, banuta--]]}},
  3973.                     {'Tarak', {monument = {32941,31182,7}, yalahar = {32916,31199,7}}},
  3974.                     {'Barry', {magician = {32884,31156,7}, sunken = {32884,31164,7}}, 'yalaharguard'},
  3975.                     {'Bruce', {alchemist = {32737,31113,7}, cemetery = {32745,31113,7}}, 'yalaharguard'},
  3976.                     {'Hal', {arena = {32688,31195,7}, alchemist = {32688,31187,7}}, 'yalaharguard'},
  3977.                     {'Oliver', {factory = {32895,31233,7}, sunken = {32895,31225,7}}, 'yalaharguard'},
  3978.                     {'Peter', {factory = {32860,31302,7}, trade = {32853,31302,7}}, 'yalaharguard'},
  3979.                     {'Reed', {cemetery = {32798,31103,7}, magician = {32806,31103,7}}, 'yalaharguard'},
  3980.                     {'Tony', {arena = {32695,31253,7}, foreigner = {32695,31260,7}}, 'yalaharguard'}}
  3981.  
  3982. function findtravelnpc()
  3983.     for i,j in ipairs(travelnpcs) do
  3984.         npcname = j[1]
  3985.         foreach creature m 'mf' do
  3986.             if m.name == npcname then
  3987.                 return m, i
  3988.             end
  3989.         end
  3990.     end
  3991.     return nil
  3992. end
  3993.  
  3994. function travel(destin, havering) -- Credits to botterxxx for finding all the destination positions.
  3995.     destin = destin:lower()
  3996.     if havering == nil and itemcount('dwarven ring') > 0 then
  3997.         havering = true
  3998.     end
  3999.     local destination
  4000.     local locationsconvert = {{{"ab'dendriel", "ab dendriel", "abdendriel"}, {"ab'dendriel", "abdendriel"}},
  4001.                               {{"libertybay", "liberty bay"}, {"liberty bay", "libertybay"}},
  4002.                               {{"port hope", "porthope"}, {"port hope", "porthope"}},
  4003.                               {{"pegleg", "peg leg", "meriana"}, {"peg leg", "pegleg"}},
  4004.                               {{"treasureisland", "treasure island"}, {"passage", "passage"}},
  4005.                               {{"isle of the kings", "isleofthekings"}, {"passage", "passage"}},
  4006.                               {{"sea serpent", "seaserpent", "seaserpents","sea serpents"}, {"hunt", "hunt"}},
  4007.                               {{"barbarian", "barbarian camp", "krimhorn"}, {"camp", "camp"}},
  4008.                               {{"femor", "femur", "femur hills", "femor hills", "femurhils", "femorhills"}, {"hills", "hills"}},
  4009.                               {{"darama"}, {"darashia", "darashia"}},
  4010.                               {{"monument tower", "monument", "trip"}, {"passage", "monument"}},
  4011.                               {{"isle of evil", "isleofevil"}, {"isle of evil", "isleofevil"}}}
  4012.     for i,j in ipairs(locationsconvert) do
  4013.         if table.find(j[1],destin) then
  4014.             destin = j[2][1]
  4015.             destination = j[2][2]
  4016.             break
  4017.         end
  4018.     end
  4019.     if not destination then
  4020.         destination = destin
  4021.     end
  4022.     local tries,maxtries = 0,math.random(1,4)
  4023.     local destinreached = false
  4024.     while not destinreached do
  4025.         local npcinfo,npcpos = findtravelnpc()
  4026.         if not npcinfo then
  4027.             printerror('There is no travel NPC on your screen.')
  4028.             return
  4029.         end
  4030.         if not travelnpcs[npcpos][2][destination] then
  4031.             printerror("The NPC '" ..npcinfo.name.. "' cant take you to '" ..destin.. "'.")
  4032.             return
  4033.         end
  4034.         local phrases = {destin, 'yes'}
  4035.         if travelnpcs[npcpos][3] then
  4036.             if travelnpcs[npcpos][3] == 'yalaharguard' then
  4037.                 phrases = {'pass', destin}
  4038.             end
  4039.         elseif npcinfo.name == 'Captain Fearless' and destin == 'darashia' then
  4040.             phrases = {destin, 'yes', 'yes'}
  4041.         elseif npcinfo.name == 'Buddel' then
  4042.             if havering then
  4043.                 phrases = {'go', destin, 'no', 'yes'}
  4044.             else
  4045.                 phrases = {'go', destin, 'yes'}
  4046.             end
  4047.         end
  4048.         if not travelnpcs[npcpos][3] then
  4049.             while npcinfo.dist > 2 do
  4050.                 reachcreature(npcinfo.name) waitping()
  4051.             end
  4052.         else
  4053.             while npcinfo.dist > 3 do
  4054.                 reachgrounditem(8617)
  4055.                 reachgrounditem(8569)
  4056.                 wait(1500)
  4057.             end
  4058.         end
  4059.         if ischannel('NPCs') then
  4060.             npcsay('hi') waitping()
  4061.         else
  4062.             say('hi') wait(2000,3000)
  4063.         end
  4064.         for i,j in ipairs(phrases) do
  4065.             npcsay(j) waitping()
  4066.         end
  4067.         waitping(5,8)
  4068.         tries = tries+1
  4069.         local desttable = (travelnpcs[npcpos][2][destination])
  4070.         destinreached = (math.abs($posx-desttable[1]) <= 2 and math.abs($posy-desttable[2]) <= 2 and $posz == desttable[3])
  4071.         if not destinreached and npcinfo.name ~= 'Buddel' and tries >= maxtries then
  4072.             printerror("Unable to travel to '" ..destin.."' trought NPC '"..npcinfo.name.."'. DestinationPos: "..desttable[1]..','..desttable[2]..','..desttable[3])
  4073.             return
  4074.         end
  4075.     end
  4076. end
  4077.  
  4078. function collectitems(bpname,...)
  4079.     local itemids = {...}
  4080.     table.id(itemids)
  4081.     if not bpname then
  4082.         bpname = ''
  4083.     elseif type(bpname) == 'number' then
  4084.         table.insert(itemids,bpname)
  4085.         bpname = ''
  4086.     end
  4087.     for j=-1,1 do
  4088.         for i=-1,1 do
  4089.             local t = topitem($posx+i,$posy+j,$posz).id
  4090.             if itemproperty(t,ITEM_PICKUPABLE) and (#itemids == 0 or table.find(itemids,t)) then
  4091.                 pausewalking(10000)
  4092.                 moveitems(t,bpname,ground($posx+i,$posy+j,$posz),100)
  4093.                 pausewalking(0)
  4094.                 break
  4095.             end
  4096.         end
  4097.     end
  4098. end
  4099.  
  4100. function usegrounditem(x,y,z)
  4101.     if not x then
  4102.         return
  4103.     elseif type(x) == 'string' then
  4104.         x = itemid(x)
  4105.     end
  4106.     if not y or not z then
  4107.         useitem(x,'ground')
  4108.     else
  4109.         useitem(topitem(x,y,z).id,ground(x,y,z))
  4110.     end
  4111.     return
  4112. end
  4113.  
  4114. function paroundignore(dist,...)
  4115.     return paround(dist)-paround(dist,...)
  4116. end
  4117.  
  4118. function maroundignore(dist,...)
  4119.     return maround(dist)-maround(dist,...)
  4120. end
  4121.  
  4122. function enchantspear(hand)
  4123.     local locationto,weaponid,handpos
  4124.     local mana = 350
  4125.     local spell = 'exeta con'
  4126.     if (itemcount(3277) == 0) or ($mp < mana) or (spell == nil) or not cooleddown('exeta con') then
  4127.         return false
  4128.     end
  4129.     if $belt.id == 0 then
  4130.         locationto = 'belt'
  4131.     else
  4132.         locationto = 'backpack'
  4133.     end
  4134.     if (hand == nil) or (hand == 'left') or (hand == 'lhand') then
  4135.         hand = $lhand
  4136.         handpos = 'lhand'
  4137.     elseif (hand == 'right') or (hand == 'rhand') then
  4138.         hand = $rhand
  4139.         handpos = 'rhand'
  4140.     end
  4141.     weaponid = hand.id
  4142.     while (hand.id ~= 0) do
  4143.         listas('Unequipping Weapon')
  4144.         moveitems(weaponid,locationto,handpos,100)
  4145.         waitping()
  4146.     end
  4147.     while (hand.id == 0) do
  4148.         listas('Equipping Spear')
  4149.         moveitems(3277,handpos,'0-15',1)
  4150.         waitping()
  4151.     end
  4152.     while (hand.id ~= 7367) and (hand.id == 3277) do
  4153.         listas('Enchanting Spear')
  4154.         cast(spell)
  4155.         waitping()
  4156.     end
  4157.     while (hand.id ~= 0) do
  4158.         listas('Unequipping Enchanted Spear')
  4159.         moveitems(7367,locationto,handpos,100)
  4160.         waitping()
  4161.     end
  4162.     while (hand.id == 0) do
  4163.         listas('Equipping Weapon')
  4164.         moveitems(weaponid,handpos,'0-15',100)
  4165.         waitping()
  4166.     end
  4167. end
  4168.  
  4169. function dropitems(pos,...)
  4170.     setlifetime(180000)
  4171.     local items = {...}
  4172.     table.id(items)
  4173.     if type(pos) == 'string' and pos:token(1) ~= 'ground' then
  4174.         table.insert(items,itemid(pos))
  4175.         pos = 'ground'
  4176.     elseif type(pos) == 'number' then
  4177.         table.insert(items,pos)
  4178.         pos = 'ground'
  4179.     end
  4180.     for i,j in ipairs(items) do
  4181.         while itemcount(j,'0-15') > 0 do
  4182.             moveitems(j,pos,'0-15',100)
  4183.         end
  4184.     end
  4185. end
  4186.  
  4187. function itemsaround(dist,...) -- by golfinhu
  4188.     local itemlist = {...}
  4189.     table.id(itemlist)
  4190.     if not dist or dist == 0 then
  4191.         dist = 7
  4192.     elseif dist > 7 or type(dist) == 'string' then
  4193.         table.insert(itemlist,itemid(dist))
  4194.         dist = 7
  4195.     end
  4196.     local total = 0
  4197.     for a=-dist,dist do
  4198.         for b=-dist,dist do
  4199.             local itemontop = topitem($posx+a,$posy+b,$posz)
  4200.             if tilehasinfo($posx+a, $posy+b, $posz) and not itemproperty(itemontop.id,ITEM_GROUND) and (table.find(itemlist,itemontop.id) or #itemlist == 0) then
  4201.                 total = total+itemontop.count
  4202.             end
  4203.         end
  4204.     end
  4205.     return total
  4206. end
  4207.  
  4208. function totalitems(location,...)
  4209.     local itemlist = {...}
  4210.     if type(location) == 'number' then
  4211.         if location > 15 then
  4212.             table.insert(itemlist,location)
  4213.             location = ''
  4214.         else
  4215.             location = tostring(location)
  4216.         end
  4217.     end
  4218.     local total = 0
  4219.     for i,j in ipairs(itemlist) do
  4220.         total = total+itemcount(j,location)
  4221.     end
  4222.     return total
  4223. end
  4224.  
  4225. function fishinice(x, y, z, pickid) -- by botterxxx
  4226.     if pickid == nil then
  4227.         pickid = 3456
  4228.     end
  4229.     if x and y and z and math.abs($posx-x) <= 7 and math.abs($posy-y) <= 5 and $posz == z then
  4230.         reachlocation(x,y,z)
  4231.         if (isitemontile(7200,x,y,z) or isitemontile(7236,x,y,z)) and not ($posx == x and $posy == y and $posz == z) then
  4232.             local id = topitem(x,y,z).id
  4233.             while id ~= 7237 do
  4234.                 if id == 7200 then
  4235.                     useitemon(pickid,id,ground(x,y,z))
  4236.                 elseif id == 7236 then
  4237.                     useitemon(3483,id,ground(x,y,z))
  4238.                 elseif not itemproperty(id,ITEM_NOTMOVEABLE) then
  4239.                     moveitems(id,ground($posx,$posy,$posz),ground(x,y,z),100)
  4240.                 else
  4241.                     return false
  4242.                 end
  4243.                 id = topitem(x,y,z).id
  4244.             end
  4245.             return true
  4246.         end
  4247.     end
  4248.     return false
  4249. end
  4250.  
  4251. --[[function movelevitate(direction,updown,times)
  4252.     local dir = {x = {n = 0, s = 0, w = -1, e = 1},
  4253.                  y = {n = -1, s = 1, w = 0, e = 0}}
  4254.     if type(times) ~= 'number' then
  4255.         times = math.random(3,5)
  4256.     end
  4257.     if direction == 'w' or direction == 'e' or direction == 'n' or direction == 's' then
  4258.         local startz = $posz
  4259.         for i=1,times do
  4260.             move(direction) waitping()
  4261.             if $posz ~= startz then
  4262.                 return true
  4263.             end
  4264.         end
  4265.         return levitate(direction, updown)
  4266.     end
  4267.     return false
  4268. end--]]
  4269.  
  4270. function getdirpos(direction,z)
  4271.     z = z or $posz
  4272.     local dir = {x = {c = 0, n = 0, s = 0, w = -1, e = 1, nw = -1, ne = 1, sw = -1, se = 1},
  4273.                  y = {c = 0, n = -1, s = 1, w = 0, e = 0, nw = -1, ne = -1, sw = 1, se = 1}}
  4274.     if dir.x[direction] then
  4275.         return {$posx+dir.x[direction],$posy+dir.y[direction],z}
  4276.     end
  4277. end
  4278.  
  4279. function movelevitate(direction)
  4280.     local dir = {x = {n = 0, s = 0, w = -1, e = 1},
  4281.                  y = {n = -1, s = 1, w = 0, e = 0}}
  4282.     if not dir.x[direction] then return false end
  4283.     local x,y,z = $posx,$posy,$posz
  4284.     local p = gettile($posx+dir.x[direction],$posy+dir.y[direction],$posz)
  4285.     local updown = 'up'
  4286.     if (p.itemcount == 1 and not itemproperty(p.item[1].id, ITEM_NOTROOFEDGE)) or p.itemcount == 0 then
  4287.         x,y,z = $posx+dir.x[direction],$posy+dir.y[direction],$posz+1
  4288.         updown = 'down'
  4289.     end
  4290.     local t = gettile(x,y,z)
  4291.     local count = 0
  4292.     print($posx,$posy,$posz,x,y,z, t.itemcount)
  4293.     for i=2, t.itemcount do
  4294.         if itemproperty(t.item[i].id, ITEM_HEIGHTED) and not itemproperty(t.item[i].id, ITEM_BLOCKWALK) then
  4295.             count = count + 1
  4296.             if count >= 3 then break end
  4297.         end
  4298.     end
  4299.     if count >= 3 then
  4300.         local i = 1
  4301.         local z = $posz
  4302.         while i <= 3 and $posz == z do
  4303.             move(direction) waitping()
  4304.             i = i+1
  4305.         end
  4306.         if $posz ~= z then
  4307.             return true
  4308.         end
  4309.     else
  4310.         return levitate(direction, updown)
  4311.     end
  4312.     return false
  4313. end
  4314.  
  4315. sealv = movelevitate
  4316.  
  4317. function sio(hppc,...)
  4318.     if not cancastspell('heal friend') then
  4319.         return false
  4320.     end
  4321.     local friends,toheal = {findcreature(...)}
  4322.     for i,j in ipairs(friends) do
  4323.         if j.hppc < hppc and j.isplayer then
  4324.             toheal = j
  4325.             hppc = j.hppc
  4326.         end
  4327.     end
  4328.     if toheal then
  4329.         local msg = 'exura sio "'..toheal.name
  4330.         if clientspellhotkey(msg) ~= 'not found' then
  4331.             cast(msg) return true
  4332.         end
  4333.         if not toheal.name:find(' +') then
  4334.             msg = 'exura sio '..toheal.name
  4335.             if clientspellhotkey(msg) ~= 'not found' then
  4336.                 cast(msg) return true
  4337.             end
  4338.         else
  4339.             printerror('Unable to find a hotkey for player: '..toheal.name)
  4340.         end
  4341.     end
  4342.     return false
  4343. end
  4344.  
  4345. function massheal(hppc,amount,considerenemies,enemylist,...)
  4346.     if not cancastspell('mass healing') then
  4347.         return false
  4348.     end
  4349.     local friends = {...}
  4350.     if type(considerenemies) ~= 'boolean' and considerenemies then
  4351.         table.insert(friends,considerenemies)
  4352.         considerenemies = nil
  4353.         if enemylist and type(enemylist) ~= 'table' then
  4354.             table.insert(friends,enemylist)
  4355.             enemylist = nil
  4356.         end
  4357.     end
  4358.     local f,e=0,0
  4359.     local creatures = {findcreaturesonspellrange('3x3','any','s')}
  4360.     for i,j in ipairs(creatures) do
  4361.         if j.hppc <= hppc and ((j.isplayer and (#friends == 0 or table.find(friends,j.name:lower()))) or (j.ismonster and table.find(friends,j.id))) then
  4362.             f = f+1
  4363.         elseif considerenemies and table.find(enemylist,j.name:lower()) then
  4364.             e = e+1
  4365.         end
  4366.     end
  4367.     if f >= amount and e == 0 then
  4368.         cast('exura gran mas res')
  4369.         return true
  4370.     end
  4371.     return false
  4372. end
  4373.  
  4374. function uh(hppc,...)
  4375.     local friends,toheal = {findcreature(...)}
  4376.     for i,j in ipairs(friends) do
  4377.         if j.hppc < hppc then
  4378.             toheal = j
  4379.             hppc = j.hppc
  4380.         end
  4381.     end
  4382.     if toheal then
  4383.         useoncreature(3160,toheal)
  4384.         return true
  4385.     end
  4386.     return false
  4387. end
  4388.  
  4389. function ih(hppc,...)
  4390.     local friends,toheal = {findcreature(...)}
  4391.     for i,j in ipairs(friends) do
  4392.         if j.hppc < hppc then
  4393.             toheal = j
  4394.             hppc = j.hppc
  4395.         end
  4396.     end
  4397.     if toheal then
  4398.         useoncreature(3152,toheal)
  4399.         return true
  4400.     end
  4401.     return false
  4402. end
  4403.  
  4404. function balance()
  4405.     return $balance
  4406. end
  4407.  
  4408. function opentrade(n, sayhi)
  4409.     if type(n) == 'boolean' then
  4410.         sayhi = n
  4411.         n = nil
  4412.     end
  4413.     n = n or math.random(3,5)
  4414.     if not ischannel('NPCs') then
  4415.         local nhi = math.random(3,5)
  4416.         local trieshi = 0
  4417.         while (not ischannel('NPCs') or sayhi) and trieshi < nhi do
  4418.             say('hi')
  4419.             local waittime = $timems+2500
  4420.             while $timems < waittime and not ischannel('NPCs') do wait(100) end
  4421.             trieshi = trieshi+1
  4422.         end
  4423.         if not ischannel('NPCs') then
  4424.             return false
  4425.         end
  4426.     end
  4427.     local tries = 0
  4428.     while not $tradeopen and tries < n do
  4429.         npcsay('trade')
  4430.         local waittime = $timems+1400
  4431.         while $timems < waittime do
  4432.             wait(100)
  4433.             if $tradeopen then
  4434.                 return true
  4435.             end
  4436.         end
  4437.         tries = tries + 1
  4438.     end
  4439.     return false
  4440. end
  4441.  
  4442. local weapons = {
  4443. axe =  {
  4444.         name = {"Angelic Axe", "Axe", "Barbarian Axe", "Battle Axe", "Beastslayer Axe", "Butcher's Axe", "Daramanian Axe", "Daramanian Waraxe", "Demonwing Axe", "Double Axe", "Dragon Lance", "Drakinata", "Dreaded Cleaver", "Dwarven Axe", "Earth Barbarian Axe", "Earth Headchopper", "Earth Heroic Axe", "Earth Knight Axe", "Earth War Axe", "Energy Barbarian Axe", "Energy Headchopper", "Energy Heroic Axe", "Energy Knight Axe", "Energy War Axe", "Executioner", "Fiery Barbarian Axe", "Fiery Headchopper", "Fiery Heroic Axe", "Fiery Knight Axe", "Fiery War Axe", "Fire Axe", "Glorious Axe", "Golden Sickle", "Great Axe", "Guardian Halberd", "Halberd", "Hand Axe", "Hatchet", "Headchopper", "Hellforged Axe", "Heroic Axe", "Icy Barbarian Axe", "Icy Headchopper", "Icy Heroic Axe", "Icy Knight Axe", "Icy War Axe", "Impaler", "Knight Axe", "Mythril Axe", "Naginata", "Noble Axe", "Obsidian Lance", "Orcish Axe", "Ornamented Axe", "Ravager's Axe", "Ravenwing", "Reaper's Axe", "Ripper Lance", "Royal Axe", "Ruthless Axe", "Scythe of the Reaper", "Sickle", "Solar Axe", "Steel Axe", "Stonecutter Axe", "Titan Axe", "Twin Axe", "Vile Axe", "War Axe", "Zaoan Halberd"},
  4445.         id = {7436, 3274, 3317, 3266, 3344, 7412, 3329, 3328, 8098, 3275, 3302, 10388, 7419, 3323, 783, 787, 786, 785, 788, 801, 804, 803, 802, 805, 7453, 665, 668, 667, 666, 669, 3320, 7454, 3306, 3303, 3315, 3269, 3268, 3276, 7380, 8096, 7389, 684, 687, 686, 685, 688, 7435, 3318, 7455, 3314, 7456, 3313, 3316, 7411, 3331, 7433, 7420, 3346, 7434, 6553, 9384, 3293, 8097, 7773, 3319, 7413, 3335, 7388, 3342, 10406},
  4446.         atk = {44, 12, 28, 25, 35, 41, 0, 39, 53, 35, 47, 47, 40, 31, 23, 34, 35, 27, 39, 23, 34, 35, 27, 39, 51, 23, 34, 35, 27, 39, 27, 40, 13, 52, 46, 35, 10, 15, 42, 51, 44, 23, 34, 35, 27, 39, 49, 33, 48, 39, 39, 34, 23, 42, 49, 45, 46, 28, 47, 50, 16, 5, 52, 21, 50, 43, 45, 43, 48, 37}
  4447.         },
  4448. sword = {
  4449.         name = {"Assassin Dagger", "Berserker", "Blacksteel Sword", "Blade of Corruption", "Bloody Edge", "Bone Sword", "Bright Sword", "Broadsword", "Carlin Sword", "Combat Knife", "Crimson Sword", "Crystal Sword", "Dagger", "Demonrage Sword", "Djinn Blade", "Dragon Slayer", "Earth Blacksteel Sword", "Earth Dragon Slayer", "Earth Mystic Blade", "Earth Relic Sword", "Earth Spike Sword", "Emerald Sword", "Energy Blacksteel Sword", "Energy Dragon Slayer", "Energy Mystic Blade", "Energy Relic Sword", "Energy Spike Sword", "Epee", "Farmer's Avenger", "Fiery Blacksteel Sword", "Fiery Dragon Slayer", "Fiery Mystic Blade", "Fiery Relic Sword", "Fiery Spike Sword", "Fire Sword", "Giant Sword", "Haunted Blade", "Havoc Blade", "Heavy Machete", "Ice Rapier", "Icy Blacksteel Sword", "Icy Dragon Slayer", "Icy Mystic Blade", "Icy Relic Sword", "Icy Spike Sword", "Incredible Mumpiz Slayer", "Jagged Sword", "Katana", "Knife", "Longsword", "Machete", "Magic Longsword", "Magic Sword", "Mercenary Sword", "Mystic Blade", "Nightmare Blade", "Pharaoh Sword", "Poet's Fencing Quill", "Pointed Rabbitslayer", "Poison Dagger", "Rapier", "Relic Sword", "Ron the Ripper's Sabre", "Runed Sword", "Sabre", "Sais", "Scimitar", "Serpent Sword", "Short Sword", "Silver Dagger", "Spike Sword", "Sword", "Templar Scytheblade", "Thaian Sword", "The Avenger", "The Epiphany", "The Justice Seeker", "Twiceslicer", "Twin Hooks", "Two Handed Sword", "Warlord Sword", "Wyvern Fang", "Zaoan Sword"},
  4450.         id = {7404, 7403, 7406, 11693, 7416, 3338, 3295, 3301, 3283, 3292, 7385, 7449, 3267, 7382, 3339, 7402, 782, 783, 781, 780, 779, 8102, 797, 798, 796, 795, 794, 3326, 9386, 663, 664, 662, 661, 660, 3280, 3281, 7407, 7405, 3330, 3284, 682, 683, 681, 680, 679, 9396, 7774, 3300, 3291, 3285, 3308, 3278, 3288, 7386, 7384, 7418, 3334, 9387, 9375, 3299, 3272, 7383, 6101, 7417, 3273, 10389, 3307, 3297, 3294, 3290, 3271, 3264, 3345, 7391, 6527, 8103, 7390, 11657, 10392, 3265, 3296, 7408, 10390},
  4451.         atk = {40, 48, 42, 48, 43, 13, 36, 26, 15, 8, 28, 35, 8, 47, 38, 44, 35, 35, 36, 34, 20, 49, 35, 35, 36, 34, 20, 37, 17, 35, 35, 36, 34, 20, 24, 46, 40, 49, 16, 42, 35, 35, 36, 34, 20, 17, 21, 16, 5, 17, 12, 55, 48, 43, 44, 46, 41, 10, 16, 16, 10, 42, 12, 45, 12, 45, 19, 18, 11, 9, 24, 14, 23, 45, 50, 50, 47, 47, 32, 30, 53, 32, 43}
  4452.          },
  4453. club = {
  4454.         name = {"Abyss Hammer", "Amber Staff", "Arcane Staff", "Banana Staff", "Battle Hammer", "Blessed Sceptre", "Bone Club", "Bonebreaker", "Brutetamer's Staff", "Chaos Mace", "Clerical Mace", "Club", "Club of the Fury", "Cranial Basher", "Crowbar", "Crystal Mace", "Daramanian Mace", "Dark Trinity Mace", "Demonbone", "Diamond Sceptre", "Drachaku", "Dragon Hammer", "Dragonbone Staff", "Earth Clerical Mace", "Earth Cranial Basher", "Earth Crystal Mace", "Earth Orcish Maul", "Earth War Hammer", "Enchanted Staff", "Energy Clerical Mace", "Energy Cranial Basher", "Energy Crystal Mace", "Energy Orcish Maul", "Energy War Hammer", "Fiery Clerical Mace", "Fiery Cranial Basher", "Fiery Crystal Mace", "Fiery Orcish Maul", "Fiery War Hammer", "Furry Club", "Giant Smithhammer", "Glutton's Mace", "Hammer of Prophecy", "Hammer of Wrath", "Heavy Mace", "Icy Clerical Mace", "Icy Cranial Basher", "Icy Crystal Mace", "Icy Orcish Maul", "Icy War Hammer", "Iron Hammer", "Jade Hammer", "Lich Staff", "Light Mace", "Lunar Staff", "Mace", "Mammoth Whopper", "Morning Star", "Northern Star", "Obsidian Truncheon", "Onyx Flail", "Orcish Maul", "Queen's Sceptre", "Sapphire Hammer", "Scythe", "Shadow Sceptre", "Silver Mace", "Skull Staff", "Skullcrusher", "Snake God's Sceptre", "Spiked Squelcher", "Staff", "Stale Bread of Ancientness", "Studded Club", "Taurus Mace", "The Stomper", "Thunder Hammer", "War Hammer"},
  4455.         id = {7414, 7426, 3341, 3348, 3305, 7429, 3337, 7428, 7379, 7427, 3311, 3270, 9385, 7415, 3304, 3333, 3327, 8099, 7431, 7387, 10391, 3322, 7430, 789, 791, 790, 792, 793, 3321, 806, 808, 807, 809, 810, 670, 672, 671, 673, 674, 7432, 3208, 9373, 7450, 3332, 3340, 689, 691, 690, 692, 693, 3310, 7422, 3343, 3325, 7424, 3286, 7381, 3282, 7409, 8100, 7421, 7392, 7410, 7437, 3453, 7451, 3312, 3324, 7423, 11692, 7452, 3289, 9376, 3336, 7425, 8101, 3309, 3279},
  4456.         atk = {47, 43, 50, 25, 24, 47, 12, 46, 35, 44, 28, 7, 16, 44, 5, 38, 21, 51, 48, 34, 46, 32, 35, 23, 36, 31, 35, 36, 39, 23, 36, 31, 35, 36, 23, 36, 31, 35, 36, 31, 24, 16, 0, 48, 49, 23, 36, 31, 35, 36, 18, 46, 40, 0, 40, 16, 30, 25, 0, 50, 45, 42, 43, 37, 8, 39, 41, 36, 51, 0, 41, 10, 18, 9, 30, 51, 49, 45}
  4457.         }       }
  4458.  
  4459. function weaponattack(id)
  4460.     local handn,hand
  4461.     if not id then
  4462.         handn, hand = findweapon()
  4463.         id = hand.id
  4464.     end
  4465.     for i,j in ipairs(weapons.axe.id) do
  4466.         if hand.id == j then
  4467.             return weapons.axe.atk[i]
  4468.         end
  4469.     end
  4470.     for i,j in ipairs(weapons.sword.id) do
  4471.         if hand.id == j then
  4472.             return weapons.sword.atk[i]
  4473.         end
  4474.     end
  4475.     for i,j in ipairs(weapons.club.id) do
  4476.         if hand.id == j then
  4477.             return weapons.club.atk[i]
  4478.         end
  4479.     end
  4480.     return 0
  4481. end
  4482.  
  4483. function strikespellinfo(creaturename, strong)
  4484.     if creaturename == '' then return nil end
  4485.     local swords
  4486.     local spells
  4487.     if strong then
  4488.         swords = 'exori gran '..getelementword(bestelement(creaturename, true))
  4489.         spells = {
  4490.                     {name="strong ice strike", words="exori gran frigo", type="instant", level=80, mp=60, price=6000, premium=true, soul=0, mlevel=0, condition=3},
  4491.                     {name="strong flame strike", words="exori gran flam", type="instant", level=70, mp=60, price=6000, premium=true, soul=0, mlevel=0, condition=3},
  4492.                     {name="strong energy strike", words="exori gran vis", type="instant", level=80, mp=60, price=7500, premium=true, soul=0, mlevel=0, condition=3},
  4493.                     {name="strong terra strike", words="exori gran tera", type="instant", level=70, mp=60, price=6000, premium=true, soul=0, mlevel=0, condition=3},
  4494.                  }
  4495.     else
  4496.         swords = 'exori '..getelementword(bestelement(creaturename, false))
  4497.         spells = {
  4498.                     {name="death strike", words="exori mort", type="instant", level=16, mp=20, price=800, premium=true, soul=0, mlevel=0, condition=3},
  4499.                     {name="physical strike", words="exori moe ico", type="instant", level=16, mp=20, price=800, premium=true, soul=0, mlevel=0, condition=3},
  4500.                     {name="ice strike", words="exori frigo", type="instant", level=15, mp=20, price=800, premium=true, soul=0, mlevel=0, condition=3},
  4501.                     {name="flame strike", words="exori flam", type="instant", level=14, mp=20, price=800, premium=true, soul=0, mlevel=0, condition=3},
  4502.                     {name="energy strike", words="exori vis", type="instant", level=12, mp=20, price=800, premium=true, soul=0, mlevel=0, condition=3},
  4503.                     {name="terra strike", words="exori tera", type="instant", level=13, mp=20, price=800, premium=true, soul=0, mlevel=0, condition=3},
  4504.                  }
  4505.     end
  4506.     local pos = table.find(spells,swords,'words')
  4507.     if not pos then
  4508.         if not noalert then printerror("Spell: \'"..name.."\' not found") end
  4509.         return
  4510.     end
  4511.     return spells[pos]
  4512. end
  4513.  
  4514. function cancastspell(spellname, who)
  4515.     local needarea,castspellinfo = false
  4516.     if type(spellname) == 'string' then
  4517.         spellname = spellname:lower()
  4518.         if spellname == 'strike' then
  4519.             castspellinfo = strikespellinfo(who.name)
  4520.         elseif spellname == 'strong strike' then
  4521.             castspellinfo = strikespellinfo(who.name,true)
  4522.         else
  4523.             castspellinfo = spellinfo(spellname)
  4524.         end
  4525.     elseif type(spellname) == 'table' then
  4526.         castspellinfo = spellname
  4527.     end
  4528.     who = findcreature(who)
  4529.     if castspellinfo then
  4530.         if who and who.id > 0 and (castspellinfo.condition and castspellinfo.condition ~= 'word') then
  4531.             needarea = true
  4532.             if $attacked.id == 0 and (table.find({'holy flash', 'divine missile', 'lightning', 'ice strike', 'flame strike', 'terra strike', 'energy strike', 'strong ice strike', 'strong flame strike', 'strong terra strike', 'strong energy strike', 'ultimate ice strike', 'ultimate flame strike', 'ultimate terra strike', 'ultimate energy strike', 'physical strike'}, castspellinfo.name)) then
  4533.                 castspellinfo.condition = 'strike'
  4534.             end
  4535.         end
  4536.         return ($mp >= castspellinfo.mp and $level >= castspellinfo.level and $mlevel >= castspellinfo.mlevel and $soul >= castspellinfo.soul and cooleddown(castspellinfo.name) and (not needarea or isonspellarea(who,castspellinfo.condition)))
  4537.     end
  4538.     return false
  4539. end
  4540.  
  4541. function moveitemonground(x,y,z,a,b,c)
  4542.     moveitems(topitem(x,y,z).id,ground(a,b,c),ground(x,y,z),100)
  4543. end
  4544.  
  4545. function wheretomoveitemtable(x,y,z,id)
  4546.     local dire = {x = {c = 0, n = 0, s = 0, w = -1, e = 1, nw = -1, ne = 1, sw = -1, se = 1},
  4547.                   y = {c = 0, n = -1, s = 1, w = 0, e = 0, nw = -1, ne = -1, sw = 1, se = 1}}
  4548.     local dirs = {'nw', 'n', 'ne', 'w', 'e', 'sw', 's', 'se'}
  4549.     z = z or $posz
  4550.     if not (x or y) or not (x > 0 or y > 0) then
  4551.         x,y = $posx,$posy
  4552.     end
  4553.     local randmove = {}
  4554.     for _,p in ipairs(dirs) do
  4555.         local i,j = dire.x[p], dire.y[p]
  4556.         local dest = {x = x+i, y = y+j}
  4557.         local tile = gettile(dest.x, dest.y, z)
  4558.         local canmove = true
  4559.         local k=1
  4560.         if tile.itemcount > 0 then
  4561.             while (k <= tile.itemcount) and canmove do
  4562.                 local itid = tile.item[k].id
  4563.                 if itid > 0 and ((itemproperty(itid, ITEM_BLOCKWALK) and (not itemproperty(itid, ITEM_TOPORDER2) or not itemproperty(itid, ITEM_HEIGHTED))) or (k == 1 and not itemproperty(itid, ITEM_NOTROOFEDGIron HammerE))) then
  4564.                     canmove = false
  4565.                 end
  4566.                 k = k+1
  4567.             end
  4568.         else
  4569.             canmove = false
  4570.         end
  4571.         if canmove then
  4572.             table.insert(randmove, {p, i, j})
  4573.         end
  4574.     end
  4575.     return randmove
  4576. end
  4577.  
  4578. function wheretomoveitem(x,y,z,id)
  4579.     if id and id == 99 then
  4580.         return wheretomovecreature(x,y,z)
  4581.     end
  4582.     z = z or $posz
  4583.     local dir
  4584.     local randmove = wheretomoveitemtable(x,y,z,id)
  4585.     if #randmove > 0 then
  4586.         return table.unpack(randmove[math.random(1,#randmove)])
  4587.     end
  4588.     return '', 0, 0
  4589. end
  4590.  
  4591. function wheretomovecreaturetable(x,y,z,id)
  4592.     local dire = {x = {c = 0, n = 0, s = 0, w = -1, e = 1, nw = -1, ne = 1, sw = -1, se = 1},
  4593.                   y = {c = 0, n = -1, s = 1, w = 0, e = 0, nw = -1, ne = -1, sw = 1, se = 1}}
  4594.     local dirs = {'nw', 'n', 'ne', 'w', 'e', 'sw', 's', 'se'}
  4595.     z = z or $posz
  4596.     if not (x or y) or not (x > 0 or y > 0) then
  4597.         x,y = $posx,$posy
  4598.     end
  4599.     local randmove = {}
  4600.     for _,p in ipairs(dirs) do
  4601.         local i,j = dire.x[p], dire.y[p]
  4602.         local dest = {x = x+i, y = y+j}
  4603.         if (id ~= 99 or (dest.x ~= $posx or dest.y ~= $posy)) then
  4604.             local tile = gettile(dest.x, dest.y, z)
  4605.             local canmove = true
  4606.             local k=1
  4607.             if tile.itemcount > 0 then
  4608.                 while (k <= tile.itemcount) and canmove do
  4609.                     local itid = tile.item[k].id
  4610.                     if itid > 0 and itemproperty(itid,ITEM_BLOCKWALK) or itemproperty(itid, ITEM_BLOCKPATHS) or itemproperty(itid, ITEM_FLOORCHANGE) or itid == 99 then
  4611.                         canmove = false
  4612.                     end
  4613.                     k = k+1
  4614.                 end
  4615.             else
  4616.                 canmove = false
  4617.             end
  4618.             if canmove then
  4619.                 table.insert(randmove, {p, i, j})
  4620.             end
  4621.         end
  4622.     end
  4623.     return randmove
  4624. end
  4625.  
  4626. function wheretomovecreature(x,y,z,dir)
  4627.     local dire = {dirs = {'c', 'n', 's', 'w', 'e', 'nw', 'ne', 'sw', 'se'},
  4628.                      x = {c = 0, n = 0, s = 0, w = -1, e = 1, nw = -1, ne = 1, sw = -1, se = 1},
  4629.                      y = {c = 0, n = -1, s = 1, w = 0, e = 0, nw = -1, ne = -1, sw = 1, se = 1}}
  4630.     local dirs = {'nw', 'n', 'ne', 'w', 'e', 'sw', 's', 'se'}
  4631.     z = z or $posz
  4632.     local randmove = {}
  4633.     if not dir then
  4634.         randmove = wheretomovecreaturetable(x,y,z)
  4635.     else
  4636.         local i,j = dire.x[dir],dire.y[dir]
  4637.         local tile = gettile(x+i,y+j,z)
  4638.         local k=1
  4639.         local canmove = true
  4640.         if tile.itemcount > 0 then
  4641.             while (k <= tile.itemcount) and canmove do
  4642.                 local itid = tile.item[k].id
  4643.                 if itid > 0 and itemproperty(itid,ITEM_BLOCKWALK) or itemproperty(itid, ITEM_BLOCKPATHS) or itemproperty(itid, ITEM_FLOORCHANGE) or itid == 99 then
  4644.                     canmove = false
  4645.                 end
  4646.                 k = k+1
  4647.             end
  4648.         else
  4649.             canmove = false
  4650.         end
  4651.         if canmove then
  4652.             return dir, i, j
  4653.         else
  4654.             return '', 0, 0
  4655.         end
  4656.     end
  4657.     if #randmove > 0 then
  4658.         return table.unpack(randmove[math.random(1,#randmove)])
  4659.     end
  4660.     return '', 0, 0
  4661. end
  4662.  
  4663. function movecreature(who, direction)
  4664.     if who then
  4665.         who = findcreature(who)
  4666.     end
  4667.     if who.dist > 1 then return false end
  4668.     local movecreatureto = {}
  4669.     local dir,dirx,diry = wheretomovecreature(who.posx,who.posy,who.posz,direction)
  4670.     if dir ~= '' then
  4671.         local topid = topitem(who.posx,who.posy,who.posz).id
  4672.         movecreatureto = {dirx+who.posx,diry+who.posy,$posz}
  4673.         if who.posz == $posz and not (movecreatureto[1] == who.posx and movecreatureto[2] == who.posy) and not (movecreatureto[1] == $posx and movecreatureto[2] == $posy) and (itemproperty(topid,ITEM_GROUND) or itemproperty(topid, ITEM_NOTMOVEABLE)) then
  4674.             moveitems(99,ground(table.unpack(movecreatureto)),ground(who.posx,who.posy,who.posz),100) wait(1200,1500)
  4675.         end
  4676.     end
  4677. end
  4678.  
  4679. function maroundspell(spelltype,direction,...)
  4680.     local monsters = {...}
  4681.     local dirs = {'w', 'e', 's', 'n', 'any'}
  4682.     table.lower(monsters)
  4683.     if type(direction) == 'string' then
  4684.         if not table.find(dirs,direction) then
  4685.             table.insert(monsters,direction:lower())
  4686.             direction = $self.dir
  4687.         end
  4688.     elseif not direction then
  4689.         direction = $self.dir
  4690.     end
  4691.     local count = 0
  4692.     foreach creature m 'mf' do
  4693.         if isonspellarea(m,spelltype,direction) and (#monsters == 0 or table.findcreature(monsters,m)) then
  4694.             count = count+1
  4695.         end
  4696.     end
  4697.     return count
  4698. end
  4699.  
  4700. function paroundspell(spelltype,direction,...)
  4701.     local players = {...}
  4702.     local dirs = {'w', 'e', 's', 'n', 'any'}
  4703.     table.lower(players)
  4704.     if type(direction) == 'string' then
  4705.         if not table.find(dirs,direction) then
  4706.             table.insert(players,direction:lower())
  4707.             direction = $self.dir
  4708.         end
  4709.     elseif not direction then
  4710.         direction = $self.dir
  4711.     end
  4712.     local count = 0
  4713.     foreach creature p 'pf' do
  4714.         if p ~= $self and isonspellarea(p,spelltype,direction) and (#players == 0 or table.findcreature(players,p)) then
  4715.             count = count+1
  4716.         end
  4717.     end
  4718.     return count
  4719. end
  4720.  
  4721. function maroundspellignore(spelltype,direction,...)
  4722.     local monsters = {...}
  4723.     local dirs = {'w', 'e', 's', 'n', 'any'}
  4724.     table.lower(monsters)
  4725.     if type(direction) == 'string' then
  4726.         if not table.find(dirs,direction) then
  4727.             table.insert(monsters,direction:lower())
  4728.             direction = $self.dir
  4729.         end
  4730.     elseif not direction then
  4731.         direction = $self.dir
  4732.     end
  4733.     local count = 0
  4734.     foreach creature m 'mf' do
  4735.         if isonspellarea(m,spelltype,direction) and (#monsters == 0 or not table.findcreature(monsters,m)) then
  4736.             count = count+1
  4737.         end
  4738.     end
  4739.     return count
  4740. end
  4741.  
  4742. function paroundspellignore(spelltype,direction,...)
  4743.     local players = {...}
  4744.     local dirs = {'w', 'e', 's', 'n', 'any'}
  4745.     table.lower(players)
  4746.     if type(direction) == 'string' then
  4747.         if not table.find(dirs,direction) then
  4748.             table.insert(players,direction:lower())
  4749.             direction = $self.dir
  4750.         end
  4751.     elseif not direction then
  4752.         direction = $self.dir
  4753.     end
  4754.     local count = 0
  4755.     foreach creature p 'pf' do
  4756.         if p ~= $self and isonspellarea(p,spelltype,direction) and (#players == 0 or not table.findcreature(players,p)) then
  4757.             count = count+1
  4758.         end
  4759.     end
  4760.     return count
  4761. end
  4762.  
  4763. function potionfriend(id,pc,dist,...)
  4764.     local friends,toheal = {findcreature(...)}
  4765.     if type(id) == 'string' then
  4766.         id = itemid(id)
  4767.     elseif type(id) == 'number' and id <= 100 and id > 0 then
  4768.         table.insert(friends,1,findcreature(dist))
  4769.         dist = pc
  4770.         pc = id
  4771.         id = nil
  4772.     end
  4773.     if not id then
  4774.         local potions = {
  4775.                             {id = 7643, level = 130},
  4776.                             {id = 239, level = 80},
  4777.                             {id = 236, level = 50},
  4778.                             {id = 266, level = 0}
  4779.                         }
  4780.         for i,j in ipairs(potions) do
  4781.             if itemcount(j.id) > 0 and $level >= j.level then
  4782.                 id = j.id
  4783.                 break
  4784.             end
  4785.         end
  4786.     end
  4787.     if type(pc) ~= 'number' or pc < 0 or pc > 100 then
  4788.         pc = 95
  4789.     end
  4790.     if type(dist) ~= 'number' or dist > 7 then
  4791.         dist = 1
  4792.     end
  4793.     table.newsort(friends,'hppc','desc')
  4794.     for i,j in ipairs(friends) do
  4795.         if j.dist <= dist then
  4796.             if j.hppc < pc or (j.hppc == pc and (not toheal or j.dist < toheal.dist)) then
  4797.                 toheal = j
  4798.                 pc = j.hppc
  4799.             else
  4800.                 break
  4801.             end
  4802.         end
  4803.     end
  4804.     if toheal then
  4805.         useoncreature(id,toheal)
  4806.         return true
  4807.     end
  4808.     return false
  4809. end
  4810.  
  4811. function currenttime()
  4812.     return os.date('%X')
  4813. end
  4814.  
  4815. function tosec(t)
  4816.     t = t or os.date('%X')
  4817.     if type(t) ~= 'string' then
  4818.         return 0
  4819.     end
  4820.     local temp = t:token(nil,':')
  4821.     local temp2 = tonumber(temp[1])*3600+tonumber(temp[2])*60
  4822.     if temp[3] then
  4823.         temp2 = temp2+tonumber(temp[3])
  4824.     end
  4825.     return temp2
  4826. end
  4827.  
  4828. function allowwalk(...)
  4829.     local t = {...}
  4830.     local walk = getsetting('Cavebot/Pathfinding/WalkableIds')
  4831.     for i,j in ipairs(t) do
  4832.         walk = walk..' '..j
  4833.     end
  4834.     setsetting('Cavebot/Pathfinding/WalkableIds',walk)
  4835. end
  4836.  
  4837. function waitping(a,b) --credits to Hardek
  4838.     a,b=a or 1.6,b or 1.9
  4839.     local p = $pingaverage
  4840.     if p == 0 then p = 150 end
  4841.     wait(p*a,p*b)
  4842. end
  4843.  
  4844. function playsoundflash(p)
  4845.     playsound(p)
  4846.     flashclient()
  4847. end
  4848.  
  4849. function finditem(a, contstart)
  4850.     a=itemid(a)
  4851.     contstart = contstart or 0
  4852.     local wheretosearch = {{'neck', $neck}, {'head', $head}, {'back', $back}, {'rhand', $rhand}, {'chest', $chest}, {'lhand', $lhand}, {'finger', $finger}, {'feet', $feet}, {'belt', $belt}}
  4853.     if itemcount(a) == 0 then
  4854.         return
  4855.     end
  4856.     for i,j in ipairs(wheretosearch) do
  4857.         if j[2].id == a then
  4858.             return j[1], j[2]
  4859.         end
  4860.     end
  4861.     for i=contstart, 15 do
  4862.         local cont = getcontainer(i)
  4863.         for j=1, cont.itemcount do
  4864.             if cont.item[j].id == a then
  4865.                 return tostring(i)
  4866.             end
  4867.         end
  4868.     end
  4869. end
  4870.  
  4871. function isdistance(x,y,z)
  4872.     x = x or 7
  4873.     y = y or x
  4874.     z = z or 0
  4875.     return math.abs($posx-$wptx) <= x and math.abs($posy-$wpty) <= y and math.abs($posz-$wptz) <= z
  4876. end
  4877.  
  4878. function islocation(x)
  4879.     x = x or 0
  4880.     return math.abs($posx-$wptx) <= x and math.abs($posy-$wpty) <= x and $posz == $wptz
  4881. end
  4882.  
  4883. function isrange(x,y)
  4884.     x = x or 1
  4885.     y = y or 1
  4886.     return $posx <= $wptx+x and $posx >= $wptx and $posy <= $wpty+y and $posy >= $wpty and $posz == $posz
  4887. end
  4888.  
  4889. function isposition(x,y,z)
  4890.     if not (x and y) then
  4891.         return false
  4892.     end
  4893.     z = z or false
  4894.     return $posx == x and $posy == y and $posz == z
  4895. end  
  4896.  
  4897. function waitcontainer(containername, newwindow)
  4898.     if newwindow or not containername then
  4899.         local i = $timems + 2000
  4900.         local curcount = windowcount(containername)
  4901.         while i >= $timems and windowcount(containername) == curcount do
  4902.             wait(100)
  4903.         end
  4904.     else
  4905.         local containernumber = tonumber(containername)
  4906.         if not containernumber then
  4907.             local i = $timems + 2000
  4908.             local curcount = windowcount(containername)
  4909.             while i >= $timems and windowcount(containername) == curcount do
  4910.                 wait(100)
  4911.             end
  4912.         else
  4913.             local cont = {}
  4914.             copycontainer(getcontainer(containernumber),cont)
  4915.             local i = $timems+2000
  4916.             local compare = true
  4917.             while i >= $timems and compare do
  4918.                 wait(200)
  4919.                 compare = comparecontainers(cont, getcontainer(containernumber))
  4920.             end
  4921.         end
  4922.     end
  4923. end
  4924.  
  4925. function copycontainer(cont1, cont2)
  4926.     cont2 = cont2 or {}
  4927.     cont2.name = cont1.name
  4928.     cont2.itemid = cont1.itemid
  4929.     cont2.maxcount = cont1.maxcount
  4930.     cont2.itemcount = cont1.itemcount
  4931.     cont2.isopen = cont1.isopen
  4932.     cont2.hashigher = cont1.hashigher
  4933.     cont2.item = {}
  4934.     for i = 1, cont1.itemcount do
  4935.         cont2.item[i] = {id = cont1.item[i].id, count = cont1.item[i].count}
  4936.     end
  4937. end
  4938.  
  4939. function comparecontainers(cont1, cont2)
  4940.     if cont1.isopen and cont2.isopen then
  4941.         if cont2.itemcount ~= cont1.itemcount or cont2.itemid ~= cont1.itemid or cont2.maxcount ~= cont1.maxcount or cont2.hashigher ~= cont1.hashigher then
  4942.             return false
  4943.         end
  4944.         for i=1, cont1.itemcount do
  4945.             if cont1.item[i].id ~= cont2.item[i].id or cont1.item[i].count ~= cont2.item[i].count then
  4946.                 return false
  4947.             end
  4948.         end
  4949.     else
  4950.         return 'Error'
  4951.     end
  4952.     return true
  4953. end
  4954.  
  4955. function num(a)
  4956.     if type(a) == 'number' then
  4957.         local sign = ''
  4958.         a=tostring(math.floor(a))
  4959.         if a:sub(1,1) == '-' then
  4960.             a = a:sub(2)
  4961.             sign = '-'
  4962.         end
  4963.         local size = a:len()
  4964.         local p = ''
  4965.         while size > 0 do
  4966.             if size-2 > 0 then
  4967.                 p=a:sub(size-2,size)..','..p
  4968.             else
  4969.                 p=a:sub(1,size)..','..p
  4970.             end
  4971.             size=size-3
  4972.         end
  4973.         return sign..p:sub(1,p:len()-1)
  4974.     else
  4975.         printerror('Bad argument #1 to \'num\' (number expected, got '..type(a)..')')
  4976.         return ''
  4977.     end
  4978. end
  4979.  
  4980. function string:attackername(returntype)
  4981.     dmg, name = self:match("You lose (%d-) .+ due to an attack by (.-)%.")
  4982.     if not name then return end
  4983.     local mtype = 'player'
  4984.     if name:sub(1,2) == 'a ' then
  4985.         name = name:sub(3)
  4986.         mtype = 'monster'
  4987.     elseif name:sub(1,3) == 'an ' then
  4988.         name = name:sub(4)
  4989.         mtype = 'monster'
  4990.     end
  4991.     if returntype then
  4992.         if returntype == 'name' then
  4993.             return name
  4994.         elseif returntype == 'type' then
  4995.             return mtype
  4996.         elseif returntype == 'dmg' then
  4997.             return tonumber(dmg)
  4998.         end
  4999.     end
  5000.     return name, mtype, tonumber(dmg)
  5001. end
  5002.  
  5003. function math:positive()
  5004.     if self < 0 then
  5005.         return 0
  5006.     end
  5007.     return self
  5008. end
  5009.  
  5010. function openbps(...)
  5011.     local bps = {...}
  5012.     for i,j in ipairs(bps) do
  5013.         openitem(j[1],j[2],j[3],j[4]) waitcontainer()
  5014.         resizewindows()
  5015.     end
  5016. end
  5017.  
  5018. function openbpslogin(...)
  5019.     local bps = {...}
  5020.     if not $connected then
  5021.         while not $connected do
  5022.             wait(300)
  5023.         end
  5024.         for i,j in ipairs(bps) do
  5025.             openitem(j[1],j[2],j[3],j[4]) waitcontainer()
  5026.             resizewindows()
  5027.         end
  5028.     end
  5029. end
  5030.  
  5031. function cooleddown(p)
  5032.     return cooldown(p) <= $pingaverage*tonumber(getsetting('Healer/Settings/PingCompensation'))/100
  5033. end
  5034.  
  5035. function mounting(p)
  5036.     p = p or $self
  5037.     return p.mount > 0
  5038. end
  5039.  
  5040. function vocation()
  5041.     local weapontype = ''
  5042.     local voc = 'unknown'
  5043.     local vocs = {mage = 5, paladin = 10, knight = 15}
  5044.     for i,j in pairs(vocs) do
  5045.         if ($maxhp-185)/($level-8) == j then
  5046.             voc = i
  5047.             break
  5048.         end
  5049.     end
  5050.     if voc == 'mage' then
  5051.         for i,j in ipairs(rods) do
  5052.             if j == $lhand.id or j == $rhand.id then
  5053.                 return 'druid'
  5054.             end
  5055.         end
  5056.         for i,j in ipairs(wands) do
  5057.             if j == $lhand.id or j == $rhand.id then
  5058.                 return 'sorcerer'
  5059.             end
  5060.         end
  5061.     end
  5062.     return voc
  5063. end
  5064.  
  5065. function bestelementweapon(creaturename) --based on Hardek's bestelement function
  5066.     local wands = {fire = {{3071, 65}, {8093, 30}, {3075, 19}}, energy = {{8092, 65}, {3073, 45}, {3074, 13}}, death = {{8094, 65}, {3072, 30}}}
  5067.     local rods = {ice = {{3067, 65}, {8083, 30}, {3070, 19}}, earth = {{8084, 65}, {3065, 45}, {3066, 13}}, death = {{8082, 65}, {3069, 30}}}
  5068.     if creaturename == '' then return 0, '' end
  5069.     local cre = creatureinfo(creaturename)
  5070.     local voc = vocation()
  5071.     if voc == 'sorcerer' then
  5072.         local best = ''
  5073.         local max = 0
  5074.         local wandsonbp = {fire = {0, 0}, energy = {0, 0}, death = {0, 0}}
  5075.         for i,j in pairs(wands) do
  5076.             for a,b in ipairs(j) do
  5077.                 if itemcount(b[1]) > 0 then
  5078.                     wandsonbp[i] = b
  5079.                     break
  5080.                 end
  5081.             end
  5082.         end
  5083.         for i,j in pairs(wandsonbp) do
  5084.             if j[1] > 0 and (cre[i..'mod']/100)*j[2] > max then
  5085.                 max = cre[i..'mod']
  5086.                 best = i
  5087.             end
  5088.         end
  5089.        
  5090.         return wandsonbp[best][1], best
  5091.     elseif voc == 'druid' then
  5092.         local best = ''
  5093.         local max = 0
  5094.         local wandsonbp = {ice = {0, 0}, earth = {0, 0}, death = {0, 0}}
  5095.         for i,j in pairs(rods) do
  5096.             for a,b in ipairs(j) do
  5097.                 if itemcount(b[1]) > 0 then
  5098.                     wandsonbp[i] = b
  5099.                     break
  5100.                 end
  5101.             end
  5102.         end
  5103.         for i,j in pairs(wandsonbp) do
  5104.             if j[1] > 0 and (cre[i..'mod']/100)*j[2] > max then
  5105.                 max = cre[i..'mod']
  5106.                 best = i
  5107.             end
  5108.         end
  5109.        
  5110.         return wandsonbp[best][1], best
  5111.     end
  5112.  
  5113.     return 0, ''
  5114. end
  5115.  
  5116. function string:concat(...)
  5117.     local words = {...}
  5118.     local ret = self
  5119.     for i=1,#words do
  5120.         ret = ret..' '..tostring(words[i])
  5121.     end
  5122.     return ret
  5123. end
  5124.  
  5125. function waitmessage(sender, msg, maxwaittime, exact, channel)
  5126.     sender = sender:lower()
  5127.     maxwaittime = maxwaittime or 10000
  5128.     if not exact then
  5129.         msg = msg:lower()
  5130.     end
  5131.     local time = 0
  5132.     local msgrecieved = false
  5133.     while time < maxwaittime do
  5134.         foreach newmessage m do
  5135.             if (m.sender:lower() == sender or sender == '') and (not channel or m.type == channel) then
  5136.                 local mcontent = m.content
  5137.                 if not exact then
  5138.                     mcontent = mcontent:lower()
  5139.                     if mcontent:find(msg) then
  5140.                         return true
  5141.                     end
  5142.                 elseif msg == mcontent then
  5143.                     return true
  5144.                 end
  5145.             end
  5146.         end
  5147.         time = time+200
  5148.         wait(200)
  5149.     end
  5150.     return false
  5151. end
  5152.  
  5153. function searchcontainerincontainer(bpnumber)
  5154.     if not bpnumber then return false end
  5155.     local temp = getcontainer(bpnumber)
  5156.     for i=temp.itemcount, 1, -1 do
  5157.         if itemproperty(temp.item[i].id, ITEM_CONTAINER) then
  5158.             return temp.item[i].id
  5159.         end
  5160.     end
  5161.     return false
  5162. end
  5163.  
  5164. function iscontainerfull(bpnumber)
  5165.     if not bpnumber then return true end
  5166.     local temp = getcontainer(bpnumber)
  5167.     return temp.maxcount == temp.itemcount
  5168. end
  5169.  
  5170. function excludecontainerid(bpnumber)
  5171.     local ret = '0-15'
  5172.     if type(bpnumber) ~= 'number' then
  5173.         return ret
  5174.     end
  5175.     if bpnumber == 0 then
  5176.         ret = '1-15'
  5177.     elseif bpnumber == 1 then
  5178.         ret = '0 '..'2-15'
  5179.     elseif bpnumber == 14 then
  5180.         ret = '0-13 '..'15'
  5181.     elseif bpnumber >= 15 then
  5182.         ret = '0-14'
  5183.     else
  5184.         ret = '0-'..(bpnumber-1)..' '..(bpnumber+1)..'-15'
  5185.     end
  5186.     return ret
  5187. end
  5188.  
  5189. function itemcountignore(iid, bpnumber)
  5190.     local count = 0
  5191.     iid = itemid(iid)
  5192.     for i=0, 15 do
  5193.         if i ~= bpnumber then
  5194.             local cont = getcontainer(i)
  5195.             if cont.isopen then
  5196.                 for j=1, cont.itemcount do
  5197.                     if cont.item[j].id == iid then
  5198.                         count = count+cont.item[j].count
  5199.                     end
  5200.                 end
  5201.             end
  5202.         end
  5203.     end
  5204.     return count
  5205. end
  5206.  
  5207. function totalitemsignore(location, ...)
  5208.     local itemlist = {...}
  5209.     if type(location) ~= 'string' then
  5210.         table.insert(itemlist,location)
  5211.         location = ''
  5212.     end
  5213.     local total = 0
  5214.     for i,j in ipairs(itemlist) do
  5215.         total = total+itemcountignore(j,location)
  5216.     end
  5217.     return total
  5218. end
  5219.  
  5220. function trueitemproperties(iid, upper)
  5221.     iid = itemid(iid)
  5222.     local properties = {ITEM_NOTROOFEDGE = 0, ITEM_TOPORDER1 = 1,ITEM_TOPORDER2 = 2,ITEM_TOPORDER3 = 3,ITEM_CONTAINER = 4,ITEM_STACKABLE = 5,ITEM_CORPSE = 6,ITEM_USEABLE = 7,ITEM_WRITEABLE = 8,ITEM_READABLE = 9,ITEM_FLUIDCONTAINER = 10,ITEM_SPLASH = 11,ITEM_BLOCKWALK = 12,ITEM_NOTMOVEABLE = 13,ITEM_BLOCKSHOTS = 14,ITEM_BLOCKPATHS = 15,ITEM_PICKUPABLE = 16,ITEM_HANGABLE = 17,ITEM_HORIZONTAL = 18,ITEM_VERTICAL = 19,ITEM_ROTATEABLE = 20,ITEM_LIGHTFONT = 21,ITEM_UNKNOWN = 22,ITEM_FLOORCHANGE = 23,ITEM_OFFSET = 24,ITEM_HEIGHTED = 25,ITEM_BIGSPRITE = 26,ITEM_UNEXIST = 27,ITEM_MINIMAP = 28,ITEM_ACTION = 29,ITEM_GROUND = 30,ITEM_BORDER = 31}
  5223.     local ret = {}
  5224.     for i,j in pairs(properties) do
  5225.         if itemproperty(iid,j) then
  5226.             if upper then
  5227.                 table.insert(ret, i)
  5228.             else
  5229.                 table.insert(ret, i:sub(6):lower())
  5230.             end
  5231.         end
  5232.     end
  5233.     local ret2 = ret[1]
  5234.     for i=2, #ret do
  5235.         ret2 = ret2..', '..ret[i]
  5236.     end
  5237.     return ret2
  5238. end
  5239.  
  5240. function sameproperties(prop,notprop)
  5241.     local properties = {}
  5242.     local p = {}
  5243.     local notproperties = notprop or {}
  5244.     if type(prop) ~= 'table' then
  5245.         prop = itemid(prop)
  5246.         for i=0, 31 do
  5247.             if itemproperty(prop, i) then
  5248.                 table.insert(properties, i)
  5249.             end
  5250.         end
  5251.     else
  5252.         properties = prop
  5253.     end
  5254.     if type(notprop) == 'string' and notprop == 'all' then
  5255.         notproperties = {}
  5256.         for i=0, 31 do
  5257.             if not table.find(properties,i) then
  5258.                 table.insert(notproperties, i)
  5259.             end
  5260.         end
  5261.     end
  5262.     for i=1, 15000 do
  5263.         local t = true
  5264.         for a,b in ipairs(properties) do
  5265.             if not itemproperty(i, b) then
  5266.                 t = false
  5267.                 break
  5268.             end
  5269.         end
  5270.         for a,b in ipairs(notproperties) do
  5271.             if itemproperty(i, b) then
  5272.                 t = false
  5273.                 break
  5274.             end
  5275.         end
  5276.         if t then
  5277.             table.insert(p, i)
  5278.         end
  5279.     end
  5280.     print(p)
  5281. end
  5282.  
  5283. function mwall(targetid, dist)
  5284.     dist = dist or 2
  5285.     local dir = {x = {n = 0, s = 0, w = -1*dist, e = 1*dist},
  5286.                  y = {n = -1*dist, s = 1*dist, w = 0, e = 0}}
  5287.     targetid = findcreature(targetid)
  5288.     if targetid.id ~= 0 then
  5289.         local pos = {targetid.posx + dir.x[targetid.dir], targetid.posy + dir.y[targetid.dir], targetid.posz}
  5290.         useitemon(3180, topitem(table.unpack(pos)).id, ground(table.unpack(pos))) wait(300)
  5291.     end
  5292. end
  5293.  
  5294. _MOVEITEMS = _MOVEITEMS or moveitems
  5295. function moveitems(iid, dest, from, amount)
  5296.     dest, from = dest or '', from or ''
  5297.     local temp = getsetting('Cavebot/Looting/MoveItemsQuickly')
  5298.     if amount and amount < 100 then
  5299.         setsetting('Cavebot/Looting/MoveItemsQuickly', 'no', false)
  5300.     end
  5301.     if dest == 'ground' and from:sub(1,6) == 'ground' then
  5302.         local temp = from:token()
  5303.         local pos
  5304.         if temp[2] then
  5305.             pos = {tonumber(temp[2]), tonumber(temp[3]), tonumber(temp[4])}
  5306.         else
  5307.             pos = {$posx,$posy,$posz}
  5308.         end
  5309.         local dir, dirx, diry = wheretomoveitem(pos[1],pos[2],pos[3], iid)
  5310.         if dir ~= '' then
  5311.             dest = ground(pos[1]+dirx,pos[2]+diry,pos[3])
  5312.         end
  5313.     end
  5314.     local ret = _MOVEITEMS(iid, dest, from, amount)
  5315.     setsetting('Cavebot/Looting/MoveItemsQuickly', temp, false)
  5316.     return ret
  5317. end
  5318.  
  5319. _EQUIPITEM = _EQUIPITEM or equipitem
  5320. function equipitem(iid, dest, from, amount)
  5321.     dest, from = dest or '', from or ''
  5322.     local temp = getsetting('Cavebot/Looting/MoveItemsQuickly')
  5323.     if amount and amount < 100 then
  5324.         setsetting('Cavebot/Looting/MoveItemsQuickly', 'no', false)
  5325.     end
  5326.     local ret = _EQUIPITEM(iid, dest, from, amount)
  5327.     setsetting('Cavebot/Looting/MoveItemsQuickly', temp, false)
  5328.     return ret
  5329. end
  5330.  
  5331. _GETTILE = _GETTILE or gettile
  5332. function gettile(x,y,z)
  5333.     x,y,z = x or $posx, y or $posy, z or $posz
  5334.     local dz = 2*(z-$posz)
  5335.     return _GETTILE(x+dz,y+dz,z)
  5336. end
  5337.  
  5338. _TOPITEM = _TOPITEM or topitem
  5339. function topitem(x,y,z)
  5340.     x,y,z = x or $posx, y or $posy, z or $posz
  5341.     local dz = 2*(z-$posz)
  5342.     local ret = _TOPITEM(x+dz,y+dz,z)
  5343.     if itemproperty(ret.id,ITEM_TOPORDER3) then
  5344.         local tileinfo = gettile(x+dz,y+dz,z)
  5345.         local pos = 1
  5346.         while pos <= tileinfo.itemcount and tileinfo.item[pos].id ~= ret.id do
  5347.             pos = pos+1
  5348.         end
  5349.         for i=pos+1, tileinfo.itemcount do
  5350.             if tileinfo.item[i].id ~= 99 then
  5351.                 ret = tileinfo.item[i]
  5352.             end
  5353.         end
  5354.     end
  5355.     return ret
  5356. end
  5357.  
  5358. _PRINT = _PRINT or print
  5359. function print(...)
  5360.     local msgs = {...}
  5361.     local toprint = ''
  5362.     for i,j in ipairs(msgs) do
  5363.         if type(j) == 'table' then
  5364.             toprint = toprint..table.stringformat(j)..' '
  5365.         else
  5366.             toprint = toprint..tostring(j)..' '
  5367.         end
  5368.     end
  5369.     _PRINT(toprint:sub(1, #toprint-1))
  5370. end
  5371.  
  5372. _PRINTERROR = _PRINTERROR or printerror
  5373. function printerror(...)
  5374.     local msgs = {...}
  5375.     local toprint = ''
  5376.     for i,j in ipairs(msgs) do
  5377.         if type(j) == 'table' then
  5378.             toprint = toprint..table.stringformat(j)..' '
  5379.         else
  5380.             toprint = toprint..tostring(j)..' '
  5381.         end
  5382.     end
  5383.     _PRINTERROR(toprint:sub(1, #toprint-1))
  5384. end
  5385.  
  5386. _LISTAS = _LISTAS or listas
  5387. function listas(...)
  5388.     local msgs = {...}
  5389.     local toprint = ''
  5390.     for i,j in ipairs(msgs) do
  5391.         if type(j) == 'table' then
  5392.             toprint = toprint..table.stringformat(j)..' '
  5393.         else
  5394.             toprint = toprint..tostring(j)..' '
  5395.         end
  5396.     end
  5397.     _LISTAS(toprint:sub(1, #toprint-1))
  5398. end
  5399.  
  5400. function areitemsontile(x,y,z,considercap,considermoveable,...) --some credits to golfinhu for considermoveable
  5401.     if not (x and y and z) then
  5402.         printerror('You must give the coordinates to check for items.')
  5403.         return false
  5404.     end
  5405.     local items = {...}
  5406.     local temp = type(considercap)
  5407.     if temp == 'string' or (temp == 'number' and temp > 1000) then
  5408.         table.insert(items,temp)
  5409.     end
  5410.     if type(considermoveable) ~= 'boolean' then
  5411.         table.insert(items, considermoveable)
  5412.     end
  5413.     table.id(items)
  5414.     if x < 10 or y < 10 then
  5415.         x = $posx-x
  5416.         y = $posy-y
  5417.         z = $posz-z
  5418.     end
  5419.     table.id(items)
  5420.     local tile = gettile(x,y,z)
  5421.     for i=2, tile.itemcount do
  5422.         temp = tile.item[i].id
  5423.         if considermoveable and itemproperty(temp,ITEM_NOTMOVEABLE) and not itemproperty(temp,ITEM_SPLASH) and not itemproperty(temp,ITEM_TOPORDER1) then
  5424.             return false
  5425.         end
  5426.         if table.find(items,temp) and (not considercap or (type(considercap) == 'boolean' and $cap >= itemweight(temp)) or (type(considercap) == 'number' and $cap >= considercap)) then
  5427.             return true
  5428.         end
  5429.     end
  5430.     return false
  5431. end
  5432.  
  5433. function collecthiddenitems(dist,...)
  5434.     local items = {...}
  5435.     if not dist then
  5436.         dist = 10
  5437.     elseif (type(dist) == 'number' and dist > 100) or (type(dist) == 'string') then
  5438.         table.insert(items, dist)
  5439.         dist = 10
  5440.     end
  5441.     table.id(items)
  5442.     local i,j
  5443.     for a=0, dist do
  5444.         j = -a
  5445.         while j <= a do
  5446.             i = -a
  5447.             while i <= a do
  5448.                 local pos = {$posx+i,$posy+j,$posz}
  5449.                 if tilehasinfo(table.unpack(pos)) and tilereachable(table.unpack(pos)) then
  5450.                     local tile = gettile(table.unpack(pos))
  5451.                     local found = 0
  5452.                     for p=1, tile.itemcount do
  5453.                         if table.find(items, tile.item[p].id) and $cap >= itemweight(tile.item[p].id) then
  5454.                             found = p
  5455.                         end
  5456.                         if itemproperty(tile.item[p].id, ITEM_NOTMOVEABLE) then
  5457.                             found = 0
  5458.                         end
  5459.                     end
  5460.                     if found > 0 then
  5461.                         local topick = tile.item[found].id
  5462.                         reachlocation(table.unpack(pos))
  5463.                         local topid = topitem(table.unpack(pos)).id
  5464.                         while topid ~= topick and isitemontile(topick, table.unpack(pos)) do
  5465.                             moveitems(topid, 'ground', ground(table.unpack(pos)), 100) waitping()
  5466.                             topid = topitem(table.unpack(pos)).id
  5467.                         end
  5468.                         moveitems(topick, '', ground(table.unpack(pos)), 100)
  5469.                         return true
  5470.                     end
  5471.                 end
  5472.                 if j ~= a and j ~= -a then
  5473.                     i = i+a*2
  5474.                 else
  5475.                     i = i+1
  5476.                 end
  5477.             end
  5478.             j = j+1
  5479.         end
  5480.     end
  5481. end
  5482. --[[
  5483. function collecthiddenitems(dist,considercap,...)
  5484.     local items = {...}
  5485.     if type(dist) ~= 'number' then
  5486.         table.insert(items, itemid(dist))
  5487.         dist = 7
  5488.     elseif dist > 10 then
  5489.         table.insert(items, dist)
  5490.         dist = 7
  5491.     end
  5492.     if type(considercap) == 'number' then
  5493.         if considercap < 1000 then
  5494.             if $cap < considercap then return false end
  5495.         else
  5496.             table.insert(items, considercap)
  5497.         end
  5498.     elseif type(considercap) == 'string' then
  5499.         table.insert(items, itemid(considercap))
  5500.     elseif type(considercap) ~= 'boolean' then
  5501.         considercap = true
  5502.     end
  5503.     table.id(items)
  5504.     for j=-dist,dist do
  5505.         for i=-dist,dist do
  5506.             local pos = {$posx+i,$posy+j,$posz}
  5507.             if tilehasinfo(table.unpack(pos)) and areitemsontile(table.unpack(pos),considercap,table.unpack(items)) and tilereachable(table.unpack(pos)) then
  5508.                 local topid = topitem(table.unpack(pos)).id
  5509.                 if not itemproperty(topid, ITEM_NOTMOVEABLE) then
  5510.                     pausewalking(0)
  5511.                     return false
  5512.                 end
  5513.                 pausewalking(40000)
  5514.                 reachlocation(table.unpack(pos))
  5515.                 repeat
  5516.                     while not table.find(items,topid) do
  5517.                         local temp = {wheretomoveitem(table.unpack(pos),topid)}
  5518.                         moveitems(topid, ground(pos[1]+temp[2],pos[2]+temp[3],z), ground(table.unpack(pos)), 100) waitping()
  5519.                         topid = topitem(table.unpack(pos)).id
  5520.                     end
  5521.                     moveitems(topid,'backpack',ground(table.unpack(pos)), 100) waitping()
  5522.                 until not areitemsontile(table.unpack(pos),considercap,table.unpack(items))
  5523.             end
  5524.         end
  5525.     end
  5526.     pausewalking(0)
  5527. end
  5528. --]]
  5529. function returnwpt(n)
  5530.     if not $wptid then return false end
  5531.     n = n or 1
  5532.     gotolabel(math.positive($wptid-n))
  5533. end
  5534.  
  5535. function castspell(spellname, who)
  5536.     if type(spellname) ~= 'table' then
  5537.         spellname = spellinfo(spellname)
  5538.     end
  5539.     if cancastspell(spellname, who) then
  5540.         cast(spellname.words)
  5541.         return true
  5542.     end
  5543.     return false
  5544. end
  5545.  
  5546. function tilehasinfo(x,y,z)
  5547.     x = x-$posx
  5548.     y = y-$posy
  5549.     return (x <= SCREEN_RIGHT and x >= SCREEN_LEFT and y >= SCREEN_TOP and y <= SCREEN_BOTTOM and z == $posz)
  5550. end
  5551.  
  5552. function eatfoodfull(location, ...)
  5553.     while true do
  5554.         if not eatfood(location, ...) then
  5555.             return false
  5556.         end
  5557.         waitping()
  5558.         foreach newmessage m do
  5559.             if m.type == MSG_STATUS and m.content == 'You are full.' then
  5560.                 return true
  5561.             end
  5562.         end
  5563.     end
  5564. end
  5565.  
  5566. function getfoodtime(id)
  5567.     id = itemid(id)
  5568.     local pos = bin2(foods, id, 1)
  5569.     if pos then
  5570.         return foods[pos][2]*1000
  5571.     end
  5572. end
  5573.  
  5574. function increasehungrytime(amount)
  5575.     amount = amount or 0
  5576.     if GLOBAL_HUNGRY == 0 or GLOBAL_HUNGRY < $timems then
  5577.         GLOBAL_HUNGRY = $timems + amount
  5578.     else
  5579.         GLOBAL_HUNGRY = GLOBAL_HUNGRY + amount
  5580.     end
  5581. end
  5582.  
  5583. function resethungrytime()
  5584.     GLOBAL_HUNGRY = 0
  5585. end
  5586.  
  5587. function gethungrytime()
  5588.     local temp = GLOBAL_HUNGRY-$timems
  5589.     if temp > 1200000 then
  5590.         return 1200000
  5591.     elseif temp < 0 then
  5592.         return 0
  5593.     else
  5594.         return temp
  5595.     end
  5596. end
  5597.  
  5598. function eatfood(location, ...)
  5599.     location = location or ''
  5600.     local foodtable = {3583, 3731, 3726, 3582, 3725, 3593, 3589, 12310, 3580, 3594, 3577, 3586, 3729, 3578, 8010, 3579, 3600, 3727, 3592, 3597, 3723, 3607, 5678, 3587, 3602, 3728, 3606, 3596, 3585, 3595, 3732, 3584, 3724, 3581, 3601, 3730, 3599, 3598, 3591, 3590, 3588}
  5601.     if (type(location) == 'number') then
  5602.         if location <= 15 then
  5603.             location = tostring(location)
  5604.         else
  5605.             foodtable = {location, ...}
  5606.             location = ''
  5607.         end
  5608.     elseif select("#", ...) > 0 then
  5609.         foodtable = {...}
  5610.     end
  5611.     if location == 'ground' then
  5612.         local foundfood = false
  5613.         for j=-1, 1 do
  5614.             for i=-1, 1 do
  5615.                 local topid = topitem($posx+i, $posy+j, $posz).id
  5616.                 local foodtime = getfoodtime(topid)
  5617.                 if isfood(topid) and foodtime+gethungrytime() <= 1200000 then
  5618.                     useitem(topid, ground($posx+i, $posy+j, $posz)) wait(100) increasehungrytime(foodtime) return true
  5619.                 end
  5620.             end
  5621.         end
  5622.     elseif location:sub(1,6) == 'ground' then
  5623.         local coord = (location:sub(8)):token()
  5624.         coord[1],coord[2],coord[3] = tonumber(coord[1]),tonumber(coord[2]),tonumber(coord[3])
  5625.         local topid = topitem(table.unpack(coord)).id
  5626.         local foodtime = getfoodtime(topid)
  5627.         if isfood(topid) and foodtime+gethungrytime() <= 1200000 then
  5628.             useitem(topid, ground(table.unpack(coord))) increasehungrytime(foodtime) wait(100) return true
  5629.         end
  5630.     else
  5631.         for i,j in ipairs(foodtable) do
  5632.             local foodtime = getfoodtime(j)
  5633.             if itemcount(j, location) > 0 and foodtime+gethungrytime() <= 1200000 then
  5634.                 useitem(j, location) increasehungrytime(foodtime) wait(100) return true
  5635.             end
  5636.         end
  5637.     end
  5638.     return false
  5639. end
  5640.  
  5641. function islocker(id)
  5642.     id = itemid(id)
  5643.     if id >= 3497 and id <= 3500 then
  5644.         return true
  5645.     end
  5646.     return false
  5647. end
  5648.  
  5649. function opendepot2(...)
  5650.     local itemtable = {...}
  5651.     table.id(itemtable)
  5652.     local walktrough = getsetting('Cavebot/Pathfinding/WalkThroughPlayers')
  5653.     setsetting('Cavebot/Pathfinding/WalkThroughPlayers', 'no', false)
  5654.     local tries, dppos, dpid = 0
  5655.     repeat
  5656.         for j=-6, 7 do
  5657.             for i=-8, 9 do
  5658.                 local pos = {$posx+i, $posy+j, $posz}
  5659.                 local topid = topitem(table.unpack(pos)).id
  5660.                 if topid >= 3497 and topid <= 3500 and tilereachable(table.unpack(pos)) then
  5661.                     reachlocation(table.unpack(pos))
  5662.                     if math.abs(pos[1]-$posx) <= 1 and math.abs(pos[2]-$posy) <= 1 and $posz == pos[3] then
  5663.                         dppos = pos
  5664.                         dpid = topid
  5665.                         break
  5666.                     end
  5667.                 end
  5668.             end
  5669.             if dpid then break end
  5670.         end
  5671.         if dpid then break end
  5672.         wait(500)
  5673.         tries = tries+1
  5674.     until tries > 5
  5675.     if not dpid then
  5676.         return false
  5677.     end
  5678.     setsetting('Cavebot/Pathfinding/WalkThroughPlayers', walktrough, false)
  5679.     tries = 0
  5680.     repeat
  5681.         openitem(dpid, ground(table.unpack(dppos))) waitcontainer('Locker')
  5682.         if windowcount('Locker') == 0 then
  5683.             local topid = topitem(table.unpack(dppos)).id
  5684.             while topid ~= dpid do
  5685.                 local dir, dirx, diry = wheretomoveitem(x,y,z,topid)
  5686.                 if not table.find(itemtable, topid) then
  5687.                     moveitems(topid, ground($posx+dirx, $posy+diry, $posz), ground(table.unpack(dppos)), 100)
  5688.                 else
  5689.                     moveitems(topid, 'backpack', ground(table.unpack(dppos)), 100)
  5690.                 end
  5691.                 wait(100)
  5692.                 topid = topitem(table.unpack(dppos)).id
  5693.             end
  5694.         else
  5695.             return true
  5696.         end
  5697.         wait(100)
  5698.         tries = tries+1
  5699.     until windowcount('Locker') > 0 or tries > 5
  5700. end
  5701.  
  5702. function waitandlogout()
  5703.     while $connected do
  5704.         while $battlesigned do
  5705.             foreach creature m 'ms' do
  5706.                 if iscreaturereachable(m) then
  5707.                     setattackmode('none', 'chase')
  5708.                     attack(m)
  5709.                     break
  5710.                 end
  5711.             end
  5712.             pausewalking(300)
  5713.             wait(100)
  5714.         end
  5715.         logout()
  5716.         wait(100)
  5717.     end
  5718. end
  5719.  
  5720. function opengrounditem(id)
  5721.     if id then
  5722.         id = itemid(id)
  5723.     end
  5724.     for i=SCREEN_LEFT, SCREEN_RIGHT do
  5725.         for j=SCREEN_TOP, SCREEN_BOTTOM do
  5726.             local x,y,z = $posx+i, $posy+j, $posz
  5727.             local topid = topitem(x,y,z).id
  5728.             if tilereachable(x,y,z) and (not id and itemproperty(topid, ITEM_ISCONTAINER)) or topid == id then
  5729.                 reachlocation(x,y,z)
  5730.                 openitem(topid, ground(x,y,z)) waitcontainer() return true
  5731.             end
  5732.         end
  5733.     end
  5734.     return false
  5735. end
  5736.  
  5737. function getbpindex(bpcolor) --by golfinhu
  5738.     local bpcolors = {'beach', 'blue', 'brocade', 'brown', 'camouflage', 'crown', 'demon', 'dragon', 'expedition', 'fur', 'golden', 'green', 'grey', 'heart', 'holding', 'minotaur', 'moon', 'orange', 'pirate', 'purple', 'red', 'santa', 'yellow', 'jewelled'}
  5739.     local bpcolor = bpcolor:lower()
  5740.     if bpcolor:find('holding') then
  5741.         bpcolor = 'holding'
  5742.     elseif bpcolor:token(1) == 'backpack' then
  5743.         bpcolor = 'brown'
  5744.     end
  5745.     local color = bpcolor:token(1)
  5746.     if not table.find(bpcolors, color) then
  5747.         printerror('Bp color not valid')
  5748.         return false
  5749.     end
  5750.     local bps = {}
  5751.     for i = 0, windowcount() - 1 do
  5752.         local bpname = getcontainer(i).name:lower()
  5753.         if bpname == 'backpack of holding' then
  5754.             bpname = 'holding backpack'
  5755.         elseif bpname == 'backpack' then
  5756.             bpname = 'brown backpack'
  5757.         end
  5758.         if bpname == color..' backpack' then
  5759.             if color == 'holding' then
  5760.                 table.insert(bps, 'backpack of holding '..i)
  5761.             else
  5762.                 table.insert(bps, color..' backpack '..i)
  5763.             end
  5764.         end
  5765.     end
  5766.     return bps
  5767. end
  5768.  
  5769. -- get the index of the backpack name --
  5770.  
  5771. function closebpcolor(bpcolor, indexs, indexe)  --by golfinhu
  5772.     if not bpcolor then
  5773.         return false
  5774.     elseif not indexs then
  5775.         if bpcolor:find('holding') then
  5776.             return closewindows('backpack of holding')
  5777.         else
  5778.             return closewindows(bpcolor:token(1)..' backpack')
  5779.         end
  5780.     end
  5781.     local indexe = indexe or indexs
  5782.     local indexs, indexe = tonumber(indexs) + 1, tonumber(indexe) + 1
  5783.     local index = getbpindex(bpcolor)
  5784.     if table.isempty(index) or #index < indexs then return false end
  5785.     for i = indexs, math.lowest(indexe,#index) do
  5786.         closewindows(index[i])
  5787.     end
  5788. end
  5789.  
  5790. -- close the specified backpack name using index by name --
  5791.  
  5792. function itemcountcorpse(corpse,...) --by golfinhu
  5793.     local itemlist = {...}
  5794.     if not corpse or #itemlist == 0 then return 0 end
  5795.     corpse = corpse:lower()
  5796.     if corpse:sub(1,4) ~= 'dead' then
  5797.         corpse = 'dead '..corpse
  5798.     end
  5799.     local total = 0
  5800.     for i = 0, windowcount() - 1 do
  5801.         local container = getcontainer(i).name:lower()
  5802.         if (corpse == 'dead' and container:find('dead')) or container == corpse then
  5803.             total = total + totalitems(tostring(i),table.unpack(itemlist))
  5804.         end
  5805.     end
  5806.     return total
  5807. end
  5808.  
  5809. function moveitemsfromcorpse(corpse,dest,amount,...) --by golfinhu
  5810.     local itemlist = {...}
  5811.     if type(dest) == 'number' then
  5812.         table.insert(itemlist,dest)
  5813.         dest = ''
  5814.     end
  5815.     if type(amount) == 'number' and amount > 100 or type(amount) == 'string' then
  5816.         table.insert(itemlist,amount)
  5817.         amount = 100
  5818.     end
  5819.     if not corpse or #itemlist == 0 then return false end
  5820.     local corpse = corpse:lower()
  5821.     local corpsetoken = corpse:token()
  5822.     if corpsetoken[1] ~= 'dead' then
  5823.         corpse = 'dead '..table.concat(corpsetoken, " ")
  5824.     end
  5825.     for i = 0, windowcount() - 1 do
  5826.         local container = getcontainer(i).name:lower()
  5827.         if (corpse == 'dead' and container:find('dead')) or container == corpse then
  5828.             for a,b in ipairs(itemlist) do
  5829.                 if itemcount(b,i) > 0 then
  5830.                     moveitems(b, dest, tostring(i), amount)
  5831.                 end
  5832.             end
  5833.         end
  5834.     end
  5835. end
  5836.  
  5837. function string:removews() --by golfinhu
  5838.     self = self:gsub("^%s*", "")
  5839.     self = self:gsub("%s*$", "")
  5840.     return self:gsub(" +", " ")
  5841. end
  5842.  
  5843.  
  5844. function string:attackmsg()
  5845.     local ttable = {dmg = 0, dealer = {name = '', type = ''}, target = {name = '', type = ''}}
  5846.     ttable.dmg, ttable.dealer.name = self:match('You lose (%w+) .+ due to an attack by (.+)%.')
  5847.     if ttable.dmg then
  5848.         ttable.target = {name = $name, type = 'player'}
  5849.         if ttable.dealer.name:sub(1,2) == 'a ' then
  5850.             ttable.dealer = {name = ttable.dealer.name:sub(3), type = 'monster'}
  5851.         elseif ttable.dealer.name:sub(1,3) == 'an ' then
  5852.             ttable.dealer = {name = ttable.dealer.name:sub(4), type = 'monster'}
  5853.         elseif ttable.dealer.name:sub(1,4) == 'the ' then
  5854.             ttable.dealer = {name = ttable.dealer.name:sub(4), type = 'monster'}
  5855.         else
  5856.             ttable.dealer.type = 'player'
  5857.         end
  5858.         ttable.dmg = tonumber(ttable.dmg)
  5859.         return ttable
  5860.     else
  5861.         ttable.target.name, ttable.dmg = self:match('(.+) loses (%w+) .+ due to your attack%.')
  5862.         if ttable.dmg then
  5863.             ttable.dealer = {name = $name, type = 'player'}
  5864.             if ttable.target.name:sub(1,2) == 'A ' then
  5865.                 ttable.target = {name = ttable.target.name:sub(3), type = 'monster'}
  5866.             elseif ttable.target.name:sub(1,3) == 'An ' then
  5867.                 ttable.target = {name = ttable.target.name:sub(4), type = 'monster'}
  5868.             elseif ttable.target.name:sub(1,4) == 'The ' then
  5869.                 ttable.target = {name = ttable.target.name:sub(4), type = 'monster'}
  5870.             else
  5871.                 ttable.target.type = 'player'
  5872.             end
  5873.             ttable.dmg = tonumber(ttable.dmg)
  5874.             return ttable
  5875.         else
  5876.             ttable.target.name, ttable.dmg, ttable.dealer.name = self:match('(.+) loses (%w+) .+ due to an attack by (.+)%.')
  5877.             if ttable.dmg then
  5878.                 if ttable.dealer.name:sub(1,2) == 'a ' then
  5879.                     ttable.dealer = {name = ttable.dealer.name:sub(3), type = 'monster'}
  5880.                 elseif ttable.dealer.name:sub(1,3) == 'an ' then
  5881.                     ttable.dealer = {name = ttable.dealer.name:sub(4), type = 'monster'}
  5882.                 elseif ttable.dealer.name:sub(1,4) == 'the ' then
  5883.                     ttable.dealer = {name = ttable.dealer.name:sub(5), type = 'monster'}
  5884.                 else
  5885.                     ttable.dealer.type = 'player'
  5886.                 end
  5887.                 if ttable.target.name:sub(1,2) == 'A ' then
  5888.                     ttable.target = {name = ttable.target.name:sub(3), type = 'monster'}
  5889.                 elseif ttable.target.name:sub(1,3) == 'An ' then
  5890.                     ttable.target = {name = ttable.target.name:sub(4), type = 'monster'}
  5891.                 elseif ttable.target.name:sub(1,4) == 'The ' then
  5892.                     ttable.target = {name = ttable.target.name:sub(5), type = 'monster'}
  5893.                 else
  5894.                     ttable.target.type = 'player'
  5895.                 end
  5896.                 ttable.dmg = tonumber(ttable.dmg)
  5897.                 return ttable
  5898.             end
  5899.         end
  5900.     end
  5901.     return {dmg = 0, dealer = {name = '', type = ''}, target = {name = '', type = ''}}
  5902. end
  5903.  
  5904. function string:healmsg()
  5905.     --Lorysa healed herself for 201 hitpoints.
  5906.     local ttable = {dmg = 0, healer = '', target = ''}
  5907.     if not self:find('heal') then return {dmg = 0, healer = '', target = ''} end
  5908.     ttable.dmg = self:match('You healed yourself for (%w+) hitpoint[s]*%.')
  5909.     if ttable.dmg then
  5910.         ttable.target, ttable.healer = $name, $name
  5911.         ttable.dmg = tonumber(ttable.dmg)
  5912.         return ttable
  5913.     else
  5914.         ttable.healer, ttable.dmg = self:match('(.+) healed h[erim]+self for (%w+) hitpoint[s]*%.')
  5915.         if ttable.dmg then
  5916.             if ttable.healer:sub(1,2) == 'A ' then
  5917.                 ttable.healer = tt.healer:sub(3)
  5918.             elseif ttable.healer:sub(1,3) == 'An ' then
  5919.                 ttable.healer = tt.healer:sub(4)
  5920.             elseif ttable.healer:sub(1,4) == 'The ' then
  5921.                 ttable.healer = tt.healer:sub(5)
  5922.             end
  5923.             ttable.target = ttable.healer
  5924.             ttable.dmg = tonumber(ttable.dmg)
  5925.             return ttable
  5926.         else
  5927.             ttable.target, ttable.dmg = self:match('You heal (.+) for (%w+) hitpoint[s]*%.')
  5928.             if ttable.dmg then
  5929.                 if ttable.target:sub(1,2) == 'a ' then
  5930.                     ttable.target = tt.target:sub(3)
  5931.                 elseif ttable.target:sub(1,3) == 'an ' then
  5932.                     ttable.target = tt.target:sub(4)
  5933.                 elseif ttable.target:sub(1,4) == 'the ' then
  5934.                     ttable.target = tt.target:sub(5)
  5935.                 end
  5936.                 ttable.healer = $name
  5937.                 ttable.dmg = tonumber(ttable.dmg)
  5938.                 return ttable
  5939.             else
  5940.                 ttable.healer, ttable.dmg = self:match('You were healed by (.+) for (%w+) hitpoint[s]*%.')
  5941.                 if ttable.dmg then
  5942.                     if ttable.healer:sub(1,2) == 'a ' then
  5943.                         ttable.healer = tt.healer:sub(3)
  5944.                     elseif ttable.healer:sub(1,3) == 'an ' then
  5945.                         ttable.healer = tt.healer:sub(4)
  5946.                     elseif ttable.healer:sub(1,4) == 'the ' then
  5947.                         ttable.healer = tt.healer:sub(5)
  5948.                     end
  5949.                     ttable.target = $name
  5950.                     ttable.dmg = tonumber(ttable.dmg)
  5951.                     return ttable
  5952.                 else
  5953.                     ttable.target, ttable.healer, ttable.dmg = self:match('(.+) was healed by (.+) for (%w+) hitpoint[s]*%.')
  5954.                     if ttable.dmg then
  5955.                         if ttable.target:sub(1,2) == 'A ' then
  5956.                             ttable.target = tt.target:sub(3)
  5957.                         elseif ttable.target:sub(1,3) == 'An ' then
  5958.                             ttable.target = tt.target:sub(4)
  5959.                         elseif ttable.target:sub(1,4) == 'The ' then
  5960.                             ttable.target = tt.target:sub(5)
  5961.                         end
  5962.                         if (ttable.healer:sub(1,2)):lower() == 'a ' then
  5963.                             ttable.healer = tt.healer:sub(3)
  5964.                         elseif (ttable.healer:sub(1,3)):lower() == 'an ' then
  5965.                             ttable.healer = tt.healer:sub(4)
  5966.                         elseif (ttable.healer:sub(1,4)):lower() == 'the ' then
  5967.                             ttable.healer = tt.healer:sub(5)
  5968.                         end
  5969.                         ttable.dmg = tonumber(ttable.dmg)
  5970.                         return ttable
  5971.                     end
  5972.                 end
  5973.             end
  5974.         end
  5975.     end
  5976.     return {dmg = 0, healer = '', target = ''}
  5977. end
  5978.  
  5979. function string:lootmsg()
  5980.     local n, temp, loot = self:match('Loot of (.+): (.+)')
  5981.     local minfoodt, valuet = 5000000, 0
  5982.     if n then
  5983.         if (n:sub(1,2)):lower() == 'a ' then
  5984.             n = n:sub(3)
  5985.         elseif (n:sub(1,3)):lower() == 'an ' then
  5986.             n = n:sub(4)
  5987.         elseif (n:sub(1,4)):lower() == 'the ' then
  5988.             n = n:sub(5)
  5989.         end
  5990.         if temp ~= 'nothing' then
  5991.             temp = temp:token(nil, ', ')
  5992.             loot = {}
  5993.             for i,j in ipairs(temp) do
  5994.                 local tt = j:find(' ') or #j+1
  5995.                 local temp1 = j:sub(1,tt-1)
  5996.                 local amount = tonumber(temp1)
  5997.                 local temp2
  5998.                 if amount then
  5999.                     temp1 = amount
  6000.                     temp2 = j:sub(tt+1, #j)
  6001.                 elseif temp1 == 'a' or temp1 == 'an' then
  6002.                     temp1 = 1
  6003.                     temp2 = j:sub(tt+1, #j)
  6004.                 else
  6005.                     temp1 = 1
  6006.                     temp2 = j
  6007.                 end
  6008.                 local pos = table.find(loot, temp2:lower(), 'name')
  6009.                 setwarning(WARNING_ITEM, false)
  6010.                 local iid = itemid(temp2)
  6011.                 setwarning(WARNING_ITEM, true)
  6012.                 if iid > 0 then
  6013.                     if iid == 2995 then
  6014.                         valuet = valuet+1000
  6015.                     elseif iid == 6558 then
  6016.                         valuet = valuet+400
  6017.                     elseif isfood(iid) then
  6018.                         local tempfoodtime = getfoodtime(iid)
  6019.                         if tempfoodtime < minfoodt then
  6020.                             minfoodt = tempfoodtime
  6021.                         end
  6022.                     else
  6023.                         valuet = valuet+itemvalue(iid)*temp1
  6024.                     end
  6025.                 end
  6026.                 if not pos then
  6027.                     table.insert(loot, {name = temp2:lower(), count = temp1})
  6028.                 else
  6029.                     loot[pos].count = loot[pos].count + temp1
  6030.                 end
  6031.             end
  6032.         else
  6033.             return {name = n:lower(), items = {}}
  6034.         end
  6035.     end
  6036.     n = n or ''
  6037.     loot = loot or {}
  6038.     return {name = n:lower(), items = loot, value = valuet, minfood = minfoodt}
  6039. end
  6040.  
  6041. function timebetween(ft,st,delay)
  6042.     local ctime,ftime,stime = tosec(),tosec(ft),tosec(st)
  6043.     delay = delay or 0
  6044.     return ctime >= ftime and ctime <= stime + delay
  6045. end
  6046.  
  6047. local ssmsgs = {'The server will be saved in 5 minutes, please come back in 10 minutes.'}
  6048. local inventoryfullmsgs = {'You cannot put more objects in this container.'}
  6049. local lowcapmsgs = {}
  6050.  
  6051. DYNAMICHUD = {aux = {x=0,y=0}, moved = {x=0,y=0}, moving = false}
  6052.  
  6053. function DYNAMICHUD:new()
  6054.     n = n or {aux = {x=0,y=0}, moved = {x=0,y=0}, moving = false}
  6055.     setmetatable(n, self)
  6056.     self.__index = self
  6057.     return n
  6058. end
  6059.  
  6060. function DYNAMICHUD:init()
  6061.     filterinput(false, true, false, false)
  6062.     function inputevents(type, v1, v2)
  6063.         if type == IEVENT_RMOUSEDOWN then
  6064.             self.moving = true
  6065.             self.aux = {x = $cursor.x-self.moved.x, y = $cursor.y-self.moved.y}
  6066.         end
  6067.         if type == IEVENT_RMOUSEUP then
  6068.             self.moving = false
  6069.         end
  6070.     end
  6071. end
  6072.  
  6073. function DYNAMICHUD:check()
  6074.     if self.moving then
  6075.         auto(10)
  6076.         self.moved = {x = $cursor.x-self.aux.y, y = $cursor.y-self.aux.y}
  6077.     end
  6078. end
  6079.  
  6080. function DYNAMICHUD:setposition(x,y)
  6081.     setposition(x+self.moved.x,self.moved.y)
  6082. end
  6083.  
  6084. function math:highest(b)
  6085.     if self > b then
  6086.         return self
  6087.     end
  6088.     return b
  6089. end
  6090.  
  6091. function math:lowest(b)
  6092.     if self < b then
  6093.         return self
  6094.     end
  6095.     return b
  6096. end
  6097.  
  6098. function creaturestringformat(cre)
  6099.     local ret = '{'
  6100.     for i,j in ipairs(_CREATUREPROPERTIES) do
  6101.         if type(cre[j]) == 'string' then
  6102.             ret = ret..j..' = "'..cre[j]..'"'..', '
  6103.         else
  6104.             ret = ret..j..' = '..tostring(cre[j])..', '
  6105.         end
  6106.     end
  6107.     return ret:sub(1,#ret-2)..'}'
  6108. end
  6109.  
  6110. function table:stringformat(tablename, separator)
  6111.     if type(self) ~= 'table' then
  6112.         return ''
  6113.     end
  6114.     separator = separator or ''
  6115.     tablename = tablename or ''
  6116.     local ret
  6117.     if tablename == '' then
  6118.         ret = '{'
  6119.     else
  6120.         ret = tablename..' = {'
  6121.     end
  6122.     local count = 0
  6123.     for i,j in ipairs(self) do
  6124.         count = count+1
  6125.         local type = type(j)
  6126.         if type == 'string' then
  6127.             ret = ret..'"'..j..'", '..separator
  6128.         elseif type == 'number' then
  6129.             ret = ret..j..', '..separator
  6130.         elseif type == 'table' then
  6131.             ret = ret..table.stringformat(j)..', '..separator
  6132.         elseif type == 'userdata' then
  6133.             if j.color1 then
  6134.                 ret = ret..creaturestringformat(j)..', '..separator
  6135.             end
  6136.         end
  6137.     end
  6138.     if count == 0 then
  6139.         for i,j in pairs(self) do
  6140.             local type = type(j)
  6141.             if type == 'string' then
  6142.                 ret = ret..i..' = "'..j..'", '..separator
  6143.             elseif type == 'number' then
  6144.                 ret = ret..i..' = '..j..', '..separator
  6145.             elseif type == 'table' then
  6146.                 ret = ret..i..' = '..table.stringformat(j)..', '..separator
  6147.             elseif type == 'userdata' then
  6148.                 if j.color1 then
  6149.                     ret = ret..i..' = '..creaturestringformat(j)..', '..separator
  6150.                 end
  6151.             end
  6152.         end
  6153.     end
  6154.     return ret:sub(1,#ret-2)..'}'
  6155. end
  6156.  
  6157. function ispk(mid)
  6158.     return mid.skull == SKULL_WHITE or mid.skull == SKULL_RED or mid.skull == SKULL_YELLOW or mid.skull == SKULL_ORANGE
  6159. end
  6160.  
  6161. function maroundfloor(dist,floor,...)
  6162.     local temp
  6163.     local creaturestocheck = {...}
  6164.     local count = 0
  6165.     dist = dist or 10
  6166.     if dist == 0 then
  6167.         dist = 10
  6168.     end
  6169.     if type(floor) == 'string' then
  6170.         temp = -(tonumber(floor))
  6171.         if not temp then
  6172.             table.insert(creaturestocheck, floor)
  6173.             floor = 7
  6174.         end
  6175.     elseif floor > 1000 then
  6176.         table.insert(creaturestocheck, floor)
  6177.         floor = 7
  6178.     end
  6179.     table.lower(creaturestocheck)
  6180.     if temp then
  6181.         if temp > 0 then
  6182.             foreach creature c 'm' do
  6183.                 local diff = c.posz-$posz
  6184.                 if diff <= temp and diff >= 0 and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and (#creaturestocheck == 0 or table.find(creaturestocheck,c.name:lower()) or table.find(creaturestocheck,c.id) or table.find(creaturestocheck,c)) then
  6185.                     count = count+1
  6186.                 end
  6187.             end
  6188.         else
  6189.             foreach creature c 'm' do
  6190.                 local diff = c.posz-$posz
  6191.                 if diff >= temp and diff <= 0 and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and (#creaturestocheck == 0 or table.find(creaturestocheck,c.name:lower()) or table.find(creaturestocheck,c.id) or table.find(creaturestocheck,c)) then
  6192.                     count = count+1
  6193.                 end
  6194.             end
  6195.         end
  6196.     else
  6197.         foreach creature c 'm' do
  6198.             local diff = c.posz-$posz
  6199.             if math.abs(diff) <= math.abs(floor) and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and (#creaturestocheck == 0 or table.find(creaturestocheck,c.name:lower()) or table.find(creaturestocheck,c.id) or table.find(creaturestocheck,c)) then
  6200.                 count = count+1
  6201.             end
  6202.         end
  6203.     end
  6204.     return count
  6205. end
  6206.  
  6207. function maroundfloorignore(dist,floor,...)
  6208.     local temp
  6209.     local creaturestocheck = {...}
  6210.     local count = 0
  6211.     dist = dist or 10
  6212.     if dist == 0 then
  6213.         dist = 10
  6214.     end
  6215.     if type(floor) == 'string' then
  6216.         temp = -(tonumber(floor))
  6217.         if not temp then
  6218.             table.insert(creaturestocheck, floor)
  6219.             floor = 7
  6220.         end
  6221.     elseif floor > 1000 then
  6222.         table.insert(creaturestocheck, floor)
  6223.         floor = 7
  6224.     end
  6225.     table.lower(creaturestocheck)
  6226.     if temp then
  6227.         if temp > 0 then
  6228.             foreach creature c 'm' do
  6229.                 local diff = c.posz-$posz
  6230.                 if diff <= temp and diff >= 0 and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and (#creaturestocheck == 0 or (not table.find(creaturestocheck,c.name:lower()) and not table.find(creaturestocheck,c.id) and not table.find(creaturestocheck,c))) then
  6231.                     count = count+1
  6232.                 end
  6233.             end
  6234.         else
  6235.             foreach creature c 'm' do
  6236.                 local diff = c.posz-$posz
  6237.                 if diff >= temp and diff <= 0 and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and (#creaturestocheck == 0 or (not table.find(creaturestocheck,c.name:lower()) and not table.find(creaturestocheck,c.id) and not table.find(creaturestocheck,c))) then
  6238.                     count = count+1
  6239.                 end
  6240.             end
  6241.         end
  6242.     else
  6243.         foreach creature c 'm' do
  6244.             local diff = c.posz-$posz
  6245.             if math.abs(diff) <= math.abs(floor) and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and (#creaturestocheck == 0 or (not table.find(creaturestocheck,c.name:lower()) and not table.find(creaturestocheck,c.id) and not table.find(creaturestocheck,c))) then
  6246.                 count = count+1
  6247.             end
  6248.         end
  6249.     end
  6250.     return count
  6251. end
  6252.  
  6253. function paroundfloor(dist,floor,...)
  6254.     local temp
  6255.     local creaturestocheck = {...}
  6256.     local count = 0
  6257.     dist = dist or 10
  6258.     if dist == 0 then
  6259.         dist = 10
  6260.     end
  6261.     if type(floor) == 'string' then
  6262.         temp = -(tonumber(floor))
  6263.         if not temp then
  6264.             table.insert(creaturestocheck, floor)
  6265.             floor = 7
  6266.         end
  6267.     elseif floor > 1000 then
  6268.         table.insert(creaturestocheck, floor)
  6269.         floor = 7
  6270.     end
  6271.     table.lower(creaturestocheck)
  6272.     if temp then
  6273.         if temp > 0 then
  6274.             foreach creature c 'p' do
  6275.                 local diff = c.posz-$posz
  6276.                 if c ~= $self and diff <= temp and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and diff >= 0 and (#creaturestocheck == 0 or table.find(creaturestocheck,c.name:lower()) or table.find(creaturestocheck,c.id) or table.find(creaturestocheck,c)) then
  6277.                     count = count+1
  6278.                 end
  6279.             end
  6280.         else
  6281.             foreach creature c 'p' do
  6282.                 local diff = c.posz-$posz
  6283.                 if c ~= $self and diff >= temp and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and diff <= 0 and (#creaturestocheck == 0 or table.find(creaturestocheck,c.name:lower()) or table.find(creaturestocheck,c.id) or table.find(creaturestocheck,c)) then
  6284.                     count = count+1
  6285.                 end
  6286.             end
  6287.         end
  6288.     else
  6289.         foreach creature c 'p' do
  6290.             local diff = c.posz-$posz
  6291.             if c ~= $self and math.abs(diff) <= math.abs(floor) and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and (#creaturestocheck == 0 or table.find(creaturestocheck,c.name:lower()) or table.find(creaturestocheck,c.id) or table.find(creaturestocheck,c)) then
  6292.                 count = count+1
  6293.             end
  6294.         end
  6295.     end
  6296.     return count
  6297. end
  6298.  
  6299. function paroundfloorignore(dist,floor,...)
  6300.     local temp
  6301.     local creaturestocheck = {...}
  6302.     local count = 0
  6303.     dist = dist or 10
  6304.     if dist == 0 then
  6305.         dist = 10
  6306.     end
  6307.     if type(floor) == 'string' then
  6308.         temp = -(tonumber(floor))
  6309.         if not temp then
  6310.             table.insert(creaturestocheck, floor)
  6311.             floor = 7
  6312.         end
  6313.     elseif floor > 1000 then
  6314.         table.insert(creaturestocheck, floor)
  6315.         floor = 7
  6316.     end
  6317.     table.lower(creaturestocheck)
  6318.     if temp then
  6319.         if temp > 0 then
  6320.             foreach creature c 'p' do
  6321.                 local diff = c.posz-$posz
  6322.                 if c ~= $self and diff <= temp and diff >= 0 and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and (#creaturestocheck == 0 or (not table.find(creaturestocheck,c.name:lower()) and not table.find(creaturestocheck,c.id) and not table.find(creaturestocheck,c))) then
  6323.                     count = count+1
  6324.                 end
  6325.             end
  6326.         else
  6327.             foreach creature c 'p' do
  6328.                 local diff = c.posz-$posz
  6329.                 if c ~= $self and diff >= temp and diff <= 0 and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and (#creaturestocheck == 0 or (not table.find(creaturestocheck,c.name:lower()) and not table.find(creaturestocheck,c.id) and not table.find(creaturestocheck,c))) then
  6330.                     count = count+1
  6331.                 end
  6332.             end
  6333.         end
  6334.     else
  6335.         foreach creature c 'p' do
  6336.             local diff = c.posz-$posz
  6337.             if c ~= $self and math.abs(diff) <= math.abs(floor) and math.highest(math.abs(c.posx-$posx), math.abs(c.posy-$posy)) <= dist and (#creaturestocheck == 0 or (not table.find(creaturestocheck,c.name:lower()) and not table.find(creaturestocheck,c.id) and not table.find(creaturestocheck,c))) then
  6338.                 count = count+1
  6339.             end
  6340.         end
  6341.     end
  6342.     return count
  6343. end
  6344.  
  6345. function bininsert1asc(tablename,value)
  6346.     if type(tablename) == 'table' then
  6347.         local left,right = 1, #tablename
  6348.         while left <= right do
  6349.             local mid = math.floor((right+left)/2)
  6350.             if tablename[mid] == value then
  6351.                 return mid
  6352.             end
  6353.             if tablename[mid] > value then
  6354.                 right = mid-1
  6355.             else
  6356.                 left = mid+1
  6357.             end
  6358.         end
  6359.     end
  6360.     return left
  6361. end
  6362.  
  6363. function bininsert2asc(tablename,value,argument,left,right)
  6364.     if type(tablename) == 'table' then
  6365.         left,right = left or 1, right or #tablename
  6366.         while left <= right do
  6367.             local mid = math.floor((right+left)/2)
  6368.             if tablename[mid][argument] == value then
  6369.                 return mid
  6370.             end
  6371.             if tablename[mid][argument] > value then
  6372.                 right = mid-1
  6373.             else
  6374.                 left = mid+1
  6375.             end
  6376.         end
  6377.     end
  6378.     return left
  6379. end
  6380.  
  6381. function bininsert1desc(tablename,value)
  6382.     if type(tablename) == 'table' then
  6383.         local left,right = 1, #tablename
  6384.         while left <= right do
  6385.             local mid = math.floor((right+left)/2)
  6386.             if tablename[mid] == value then
  6387.                 return mid
  6388.             end
  6389.             if tablename[mid] < value then
  6390.                 right = mid-1
  6391.             else
  6392.                 left = mid+1
  6393.             end
  6394.         end
  6395.     end
  6396.     return left
  6397. end
  6398.  
  6399. function bininsert2desc(tablename,value,argument,left,right)
  6400.     if type(tablename) == 'table' then
  6401.         local left,right = left or 1, right or #tablename
  6402.         while left <= right do
  6403.             local mid = math.floor((right+left)/2)
  6404.             if tablename[mid][argument] == value then
  6405.                 return mid
  6406.             end
  6407.             if tablename[mid][argument] < value then
  6408.                 right = mid-1
  6409.             else
  6410.                 left = mid+1
  6411.             end
  6412.         end
  6413.     end
  6414.     return left
  6415. end
  6416.  
  6417. function table:insertsorted(value, argument, order, disallowduplicated)
  6418.     if type(self) == 'table' then
  6419.         if type(value) == 'userdata' or type(value) == 'table' then
  6420.             if argument then
  6421.                 if type(argument) == 'table' then
  6422.                     for i=1,#argument do
  6423.                         if type(argument[i]) ~= 'table' then
  6424.                             argument[i] = {argument[i], 'asc'}
  6425.                         elseif not argument[i][2] then
  6426.                             argument[i][2] = 'asc'
  6427.                         end
  6428.                     end
  6429.                     if argument[1][2] == 'asc' then
  6430.                         inssortedasc_1(self, value, argument)
  6431.                     else
  6432.                         inssorteddesc_1(self, value, argument)
  6433.                     end
  6434.                 else
  6435.                     if order == true then
  6436.                         disallowduplicated = true
  6437.                         order = false
  6438.                     end
  6439.                     order = order or 'asc'
  6440.                     local postoinsert
  6441.                     if order == 'asc' then
  6442.                         postoinsert = bininsert2asc(self, value, argument)
  6443.                     else
  6444.                         postoinsert = bin2insertdesc(self, value, argument)
  6445.                     end
  6446.                     table.insert(self, postoinsert, value)
  6447.                     return true
  6448.                 end
  6449.             else
  6450.                 printerror('You must give some argument to order according to.')
  6451.             end
  6452.         else
  6453.             if argument then
  6454.                 local temp = order
  6455.                 order = argument
  6456.                 disallowduplicated = temp
  6457.             end
  6458.             order = order or 'asc'
  6459.             local postoinsert
  6460.             if order == 'asc' then
  6461.                 postoinsert = bin1insertasc(self, value)
  6462.             else
  6463.                 postoinsert = bin1insertdesc(self, value)
  6464.             end
  6465.             table.insert(self, postoinsert, value)
  6466.             return true
  6467.         end
  6468.     end
  6469.     return false
  6470. end
  6471.  
  6472. function inssortedasc_1(tablename, value, argument)
  6473.     local i = #tablename
  6474.     local arg = argument[1][1]
  6475.     while i >= 1 do
  6476.         if (tablename[i][arg] > value[arg]) then
  6477.             tablename[i+1] = tablename[i]
  6478.         elseif (tablename[i][arg] == value[arg]) then
  6479.             if (#argument > 1) then
  6480.                 if argument[2][2] == 'asc' then
  6481.                     return inssortedasc_2(tablename, value, argument, 2, i)
  6482.                 else
  6483.                     return inssorteddesc_2(tablename, value, argument, 2, i)
  6484.                 end
  6485.             else
  6486.                 tablename[i+1] = value
  6487.                 return true
  6488.             end
  6489.         else
  6490.             tablename[i+1] = value
  6491.             return true
  6492.         end
  6493.         i = i-1
  6494.     end
  6495.     tablename[i+1] = value
  6496.     return true
  6497. end
  6498.  
  6499. function inssortedasc_2(tablename, value, argument, argpos, right)
  6500.     local i = right
  6501.     local arg1,arg2 = argument[argpos][1], argument[argpos-1][1]
  6502.     while i >= 1 and tablename[i][arg2] == value[arg2] do
  6503.         if (tablename[i][arg1] > value[arg1]) then
  6504.             tablename[i+1] = tablename[i]
  6505.         elseif (tablename[i][arg1] == value[arg1]) then
  6506.             if (argpos < #argument) then
  6507.                 if argument[argpos+1][2] == 'asc' then
  6508.                     return inssortedasc_2(tablename, value, argument, argpos+1, i)
  6509.                 else
  6510.                     return inssorteddesc_2(tablename, value, argument, argpos+1, i)
  6511.                 end
  6512.             else
  6513.                 tablename[i+1] = value
  6514.                 return true
  6515.             end
  6516.         else
  6517.             tablename[i+1] = value
  6518.             return true
  6519.         end
  6520.         i = i-1
  6521.     end
  6522.     tablename[i+1] = value
  6523.     return true
  6524. end
  6525.  
  6526. function inssorteddesc_1(tablename, value, argument)
  6527.     local i = #tablename
  6528.     local arg = argument[1][1]
  6529.     while i >= 1 do
  6530.         if (tablename[i][arg] < value[arg]) then
  6531.             tablename[i+1] = tablename[i]
  6532.         elseif (tablename[i][arg] == value[arg]) then
  6533.             if (#argument > 1) then
  6534.                 if argument[2][2] == 'asc' then
  6535.                     return inssortedasc_2(tablename, value, argument, 2, i)
  6536.                 else
  6537.                     return inssorteddesc_2(tablename, value, argument, 2, i)
  6538.                 end
  6539.             else
  6540.                 tablename[i+1] = value
  6541.                 return true
  6542.             end
  6543.         else
  6544.             tablename[i+1] = value
  6545.             return true
  6546.         end
  6547.         i = i-1
  6548.     end
  6549.     tablename[i+1] = value
  6550.     return true
  6551. end
  6552.  
  6553. function inssorteddesc_2(tablename, value, argument, argpos, right)
  6554.     local i = right
  6555.     local arg1,arg2 = argument[argpos][1], argument[argpos-1][1]
  6556.     while i >= 1 and tablename[i][arg2] == value[arg2] do
  6557.         if (tablename[i][arg1] < value[arg1]) then
  6558.             tablename[i+1] = tablename[i]
  6559.         elseif (tablename[i][arg1] == value[arg1]) then
  6560.             if (argpos < #argument) then
  6561.                 if argument[argpos+1][2] == 'asc' then
  6562.                     return inssortedasc_2(tablename, value, argument, argpos+1, i)
  6563.                 else
  6564.                     return inssorteddesc_2(tablename, value, argument, argpos+1, i)
  6565.                 end
  6566.             else
  6567.                 tablename[i+1] = value
  6568.                 return true
  6569.             end
  6570.         else
  6571.             tablename[i+1] = value
  6572.             return true
  6573.         end
  6574.         i = i-1
  6575.     end
  6576.     tablename[i+1] = value
  6577.     return true
  6578. end
  6579.  
  6580. function ringinuse(iid)
  6581.     local rings = {{3092, 3095}, {3091, 3094}, {3093, 3096}, {3052, 3089}, {3098, 3100}, {3097, 3099}, {3051, 3088}, {3053, 3090}, {3049, 3086}, {9593, 9593}, {9393, 9392}, {3007, 3007}, {6299, 6300}, {9585, 9585}, {3048, 3048}, {3050, 3087}, {3245, 3245}, {3006, 3006}, {349, 349}, {3004, 3004}}
  6582.     local temp = table.find(rings, itemid(iid), 1)
  6583.     if temp then
  6584.         return rings[temp][2]
  6585.     end
  6586.     return 0
  6587. end
  6588.  
  6589. function castspellarea(spell, amount, ignoreplayers, ...)
  6590.     if type(spell) ~= 'table' then
  6591.         spell = spellinfo(spell)
  6592.     end
  6593.     if cancastspell(spell) then
  6594.         if type(amount) ~= 'number' then
  6595.             amount = 0
  6596.         end
  6597.         local monsters = {...}
  6598.         if type(ignoreplayers) ~= 'boolean' then
  6599.             table.insert(monsters, ignoreplayers)
  6600.             ignoreplayers = false
  6601.         end
  6602.         local needdir = false
  6603.         if table.find({'front', 'bigbeam', 'smallbeam', 'bigwave', 'smallwave', 'strike'}, spell.condition) then
  6604.             needdir = true
  6605.         end
  6606.         if needdir then
  6607.             local count = {w = 0, e = 0, n = 0, s = 0}
  6608.             foreach creature m 's' do
  6609.                 for i,j in pairs(count) do
  6610.                     if isonspellarea(m, spell.condition, i) then
  6611.                         if m.ismonster then
  6612.                             if #monsters == 0 or table.find(monsters,m.name:lower()) or table.find(monsters,m.id) or table.find(monsters,m) then
  6613.                                 count[i] = count[i]+1
  6614.                             end
  6615.                         elseif not ignoreplayers then
  6616.                             return false
  6617.                         end
  6618.                     end
  6619.                 end
  6620.             end
  6621.             local bestdir = $self.dir
  6622.             for i,j in pairs(count) do
  6623.                 if j > count[bestdir] then
  6624.                     bestdir = i
  6625.                 end
  6626.             end
  6627.             if count[bestdir] >= amount then
  6628.                 while $self.dir ~= bestdir do turn(bestdir) wait(50,100) end
  6629.                 cast(spell.words)
  6630.                 return true
  6631.             end
  6632.         else
  6633.             local count = 0
  6634.             foreach creature m 's' do
  6635.                 if isonspellarea(m, spell.condition) then
  6636.                     if m.ismonster then
  6637.                         if #monsters == 0 or table.find(monsters,m.name:lower()) or table.find(monsters,m.id) or table.find(monsters,m) then
  6638.                             count = count+1
  6639.                         end
  6640.                     elseif not ignoreplayers then
  6641.                         return false
  6642.                     end
  6643.                 end
  6644.             end
  6645.             if count >= amount then
  6646.                 cast(spell.words)
  6647.                 return true
  6648.             end
  6649.         end
  6650.     end
  6651. end
  6652.  
  6653. function tilewalkable(x,y,z)
  6654.     x,y,z = x or $posx, y or $posy, z or $posz
  6655.     if type(x) == 'string' then
  6656.         local dirx = {c = 0, n = 0, s = 0, w = -1, e = 1, nw = -1, ne = 1, sw = -1, se = 1}
  6657.         local diry = {c = 0, n = -1, s = 1, w = 0, e = 0, nw = -1, ne = -1, sw = 1, se = 1}
  6658.         for i,j in pairs(dirx) do
  6659.             if i == x then
  6660.                 x = j
  6661.                 y = diry[i]
  6662.                 break
  6663.             end
  6664.         end
  6665.         z = $posz
  6666.     end
  6667.     local tile = gettile(x,y,z)
  6668.     local v = 1
  6669.     if tile.item[v].id == 0 or itemproperty(tile.item[v].id, ITEM_FLOORCHANGE) or not itemproperty(tile.item[v].id, ITEM_GROUND) then
  6670.         return false
  6671.     end
  6672.     v = 2
  6673.     if itemproperty(tile.item[v].id, ITEM_TOPORDER1) then
  6674.         v = 3
  6675.     end
  6676.     if itemproperties(tile.item[v].id, ITEM_MINIMAP, ITEM_NOTMOVEABLE) then
  6677.         if itemproperty(tile.item[v].id, ITEM_BLOCKPATHS) and not itemproperty(tile.item[v].id, ITEM_GROUND) then
  6678.             return false
  6679.         elseif itemproperty(tile.item[v].id, ITEM_TOPORDER2) and itemproperty(tile.item[v].id, ITEM_BLOCKPATHS) and (itemproperty(tile.item[v].id, ITEM_HEIGHTED) or itemproperty(tile.item[v].id, ITEM_LIGHTFONT)) then
  6680.             return false
  6681.         end
  6682.     end
  6683.     for i=1, tile.itemcount do
  6684.         if (itemproperty(tile.item[i].id, ITEM_BLOCKWALK) or (tile.item[i].id == 99 and (tile.item[i].count > 0x40000000 or getsetting('Cavebot/Pathfinding/WalkThroughPlayers') == 'no'))) then
  6685.             return false
  6686.         end
  6687.     end
  6688.     return true
  6689. end
  6690.  
  6691. function trapped()
  6692.     if not $cavebot or ($wpttype == 'action') or ($wptx == 0) then
  6693.         for j=-1, 1 do
  6694.             for i=-1, 1 do
  6695.                 if i ~= 0 or j ~= 0 then
  6696.                     if tilewalkable($posx+i,$posy+j,$posz) then
  6697.                         return false
  6698.                     end
  6699.                 end
  6700.             end
  6701.         end
  6702.         return true
  6703.     else
  6704.         if tilereachable($wptx,$wpty,$wptz,true) then
  6705.             return false
  6706.         end
  6707.         return true
  6708.     end
  6709. end
  6710.  
  6711. function randomize(ttable)
  6712.     local value = 0
  6713.     if type(ttable) == 'table' then
  6714.         value = math.random(table.unpack(ttable))
  6715.     end
  6716.     return value
  6717. end
  6718.  
  6719. _USEITEMON = _USEITEMON or useitemon
  6720. function useitemon(fromid,toid,todest,fromdest)
  6721.     toid, todest, fromdest = toid or 0, todest or '', fromdest or ''
  6722.     if toid == 0 or not toid then
  6723.         local tableequip = {{'rhand', $rhand}, {'lhand', $lhand}, {'head', $head}, {'chest', $chest}, {'legs', $legs}, {'feet', $feet}, {'finger', $finger}, {'neck', $neck}, {'belt', $belt}, {'back', $back}}
  6724.         local temp = table.find(tableequip, todest, 1)
  6725.         if temp then
  6726.             toid = tableequip[temp][2].id
  6727.         end
  6728.     end
  6729.     return _USEITEMON(fromid,toid,todest,fromdest)
  6730. end
  6731.  
  6732. ------------------------------Raphael.lua---------------------------------
  6733.  
  6734. -- Raphael's Library v2.9.7
  6735. --      Last updated: 08/21 - 01:54
  6736.  
  6737. --[[
  6738.  * Changelog v2.9.7
  6739.  *
  6740.  * - Fixed a small mistake (getting tired of it) on the library versions workaround.
  6741.  *
  6742. --]]
  6743.  
  6744.  
  6745.  
  6746. RAPHAEL_LIB = "2.9.7"
  6747. print('Raphael\'s Library loaded. Last updated: 08/21 - 01:54 (v' .. RAPHAEL_LIB .. ')')
  6748.  
  6749. table.unpack = table.unpack or unpack
  6750. unpack = unpack or table.unpack
  6751.  
  6752. f = false
  6753. LUCAS_LIB = tonumber((LUCAS_LIB:gsub('%.', function() if not f then f = true return '.' else return '' end end)))
  6754. f = false
  6755. RAPHAEL_LIB = tonumber((RAPHAEL_LIB:gsub('%.', function() if not f then f = true return '.' else return '' end end)))
  6756.  
  6757. -- HUD Events
  6758. iEvent_MouseEnter = IEVENT_MOUSEENTER
  6759. iEvent_MouseLeave = IEVENT_MOUSELEAVE
  6760. iEvent_MouseMove  = IEVENT_MOUSEMOVE
  6761. iEvent_MiddleDown = IEVENT_MMOUSEDOWN
  6762. iEvent_MiddleUp   = IEVENT_MMOUSEUP
  6763. iEvent_RightDown  = IEVENT_RMOUSEDOWN
  6764. iEvent_RightUp    = IEVENT_RMOUSEUP
  6765. iEvent_LeftDown   = IEVENT_LMOUSEDOWN
  6766. iEvent_LeftUp     = IEVENT_LMOUSEUP
  6767. iEvent_KeyDown    = IEVENT_KEYDOWN
  6768. iEvent_KeyUp      = IEVENT_KEYUP
  6769.  
  6770.  
  6771. local skills = {
  6772.     magic = {$mlevelpc, nil, nil, nil, nil, nil, nil},
  6773.     fist = {$fistpc, nil, nil, nil, nil, nil, nil},
  6774.     club = {$clubpc, nil, nil, nil, nil, nil, nil},
  6775.     sword = {$swordpc, nil, nil, nil, nil, nil, nil},
  6776.     axe = {$axepc, nil, nil, nil, nil, nil, nil},
  6777.     distance = {$distancepc, nil, nil, nil, nil, nil, nil},
  6778.     shielding = {$shieldingpc, nil, nil, nil, nil, nil, nil},
  6779.     fishing = {$fishingpc, nil, nil, nil, nil, nil, nil}
  6780. }
  6781.  
  6782. function flasks() -- Working
  6783.     return itemcount(283) +  itemcount(284) + itemcount(285)
  6784. end
  6785.  
  6786. function dropflasks() -- Working
  6787.     local flaskids = {283, 284, 285}
  6788.     for i = 1, #flaskids do
  6789.         if itemcount(flaskids[i]) > 0 then
  6790.             moveitems(flaskids[i], 'ground')
  6791.             waitping()
  6792.         end
  6793.     end
  6794. end
  6795.  
  6796. function gold() -- Working
  6797.     return itemcount(3031) + itemcount(3035) * 100 + itemcount(3043) * 10000
  6798. end
  6799.  
  6800. function moveitemlist(locationto, locationfrom, ...) -- Working
  6801.     local t = {...}
  6802.     for i = 1, #t do
  6803.         if itemcount(t[i], locationfrom or '') > 0 then
  6804.             moveitems(t[i], locationto, locationfrom or '')
  6805.             waitping()
  6806.         end
  6807.     end
  6808. end
  6809.  
  6810. function npctalk(...) -- Working
  6811.     local arg = {...}
  6812.  
  6813.     -- Adjust settings to lower tab pressingtime.
  6814.     local presswait = get('PressWaitTime')
  6815.     set('PressWaitTime', '200 to 300')
  6816.  
  6817.     -- Checks for caps lock and normal wait parameters.
  6818.     local cc, nw
  6819.     if type(arg[#arg]) == 'boolean' then
  6820.         if type(arg[#arg-1]) == 'boolean' then
  6821.             if arg[#arg] then
  6822.                 nw = true
  6823.             end
  6824.             if arg[#arg-1] then
  6825.                 cc = true
  6826.             end
  6827.             table.remove(arg)
  6828.         elseif arg[#arg] then
  6829.             cc = true
  6830.         end
  6831.         table.remove(arg)
  6832.     end
  6833.  
  6834.     local f
  6835.     -- Sets the desired wait method.
  6836.     if nw then
  6837.         f = function()
  6838.                 waitping()
  6839.                 return true
  6840.             end
  6841.     else
  6842.         f = function(msg, type)
  6843.                 local c = 0
  6844.                 while c < 30 do
  6845.                     foreach newmessage m do
  6846.                         if m.sender == $name and m.content == msg and m.type == type then
  6847.                             return true
  6848.                         end
  6849.                     end
  6850.                     c = c + 1
  6851.                     wait(90, 110)
  6852.                 end
  6853.                 return false
  6854.             end
  6855.  
  6856.         -- Makes all args string
  6857.         for k, v in ipairs(arg) do
  6858.             v = tostring(v)
  6859.         end
  6860.     end
  6861.  
  6862.     -- Checks the caps lock
  6863.     if cc then
  6864.         press("a")
  6865.         wait(200, 400)
  6866.         if $typedtext == "A" then
  6867.             table.upper(arg)
  6868.             --press("[CAPSLOCK]")
  6869.             --waitping()
  6870.         end
  6871.     end
  6872.  
  6873.     local p = false
  6874.     if not ischannel('NPCs') then
  6875.         while not p do
  6876.             say('Default', arg[1])
  6877.             p = f(arg[1], MSG_DEFAULT)
  6878.         end
  6879.         table.remove(arg, 1)
  6880.         wait(400, 600)
  6881.     end
  6882.  
  6883.     for k, v in ipairs(arg) do
  6884.         p = false
  6885.         while not p do
  6886.             say('NPCs', v)
  6887.             p = f(v, MSG_SENT)
  6888.             if not p then
  6889.                 if not ischannel('NPCs') then
  6890.                     npctalk(select(k, ...))
  6891.                     return
  6892.                 end
  6893.             end
  6894.         end
  6895.     end
  6896.  
  6897.     set('PressWaitTime', presswait)
  6898.  
  6899. end
  6900.  
  6901. function skilltime(skilltype) -- Needs to be remade/adjusted.
  6902.     local percent = {magic = $mlevelpc, fist = $fistpc, club = $clubpc, sword = $swordpc, axe = $axepc, distance = $distancepc, shielding = $shieldingpc, fishing = $fishingpc}
  6903.     local skillpc = percent[skilltype]
  6904.     if skillpc ~= skills[skilltype][1] then
  6905.         if skillpc ~= 0 then
  6906.             if skills[skilltype][3] then
  6907.                 skills[skilltype][2] = ($timems - skills[skilltype][3]) * (100 - skillpc) / (skillpc - skills[skilltype][1])
  6908.             else
  6909.                 skills[skilltype][2] = nil
  6910.             end
  6911.         end
  6912.         skills[skilltype][1] = skillpc
  6913.         skills[skilltype][3] = $timems
  6914.     end
  6915.     if skills[skilltype][2] then
  6916.         return math.max(math.floor((skills[skilltype][2] - ($timems - skills[skilltype][3])) / 1000), 0)
  6917.     else
  6918.         return 0
  6919.     end
  6920. end
  6921.  
  6922. function keyid(key) -- Working -- Find full list at: http://api.farmanager.com/en/winapi/virtualkeycodes.html
  6923.     local keys = {MOUSELEFT = 0x01, MOUSERIGHT = 0x02, MOUSEMIDDLE = 0x04, BACKSPACE = 0x08, TAB = 0x09, CLEAR = 0x0C, ENTER = 0x0D, SHIFT = 0x10, CTRL = 0x11, ALT = 0x12, PAUSE = 0x13, CAPSLOCK = 0x14, ESC = 0x1B, SPACE = 0x20, PAGEUP = 0x21, PAGEDOWN = 0x22, END = 0x25, HOME = 0x24, LEFTARROW = 0x25, UPARROW = 0x26, RIGHTARROW = 0x27, DOWNARROW = 0x28, SELECT = 0x29, PRINT = 0x2A, ExECUTE = 0x2B, PRINTSCREEN =0x2C, INSERT = 0x2D, DELETE = 0x2E, HELP = 0x2F, A = 0x41, B = 0x42, C = 0x43, D = 0x44, E = 0x45, F = 0x46, G = 0x47, H = 0x48, I = 0x49, J = 0x4A, K = 0x4B, L = 0x4C, M = 0x4D, N = 0x4E, O = 0x4F, P = 0x50, Q = 0x51, R = 0x52, S = 0x53, T = 0x54, U = 0x55, V = 0x56, W = 0x57, x = 0x58, Y = 0x59, Z = 0x5A, SLEEP = 0x5F, NUM0 = 0x60, NUM1 = 0x61, NUM2 = 0x62, NUM3 = 0x63, NUM4 = 0x64, NUM5 = 0x65, NUM6 = 0x66, NUM7 = 0x67, NUM8 = 0x68, NUM9 = 0x69, MULTIPLY = 0x6A, ADD = 0x6B, SEPARATOR = 0x6C, SUBTRACT = 0x6D, DECIMAL = 0x6E, DIVIDE = 0x6F, F1 = 0x70, F2 = 0x71, F3 = 0x72, F4 = 0x73, F5 = 0x74, F6 = 0x75, F7 = 0x76, F8 = 0x77, F9 = 0x78, F10 = 0x89, F11 = 0x7A, F12 = 0x7B, F13 = 0x7C, F14 = 0x7D, F15 = 0x7E, F16 = 0x7F, F17 = 0x80, F18 = 0x81, F19 = 0x82, F20 = 0x83, F21 = 0x84, F22 = 0x85, F23 = 0x86, F24 = 0x87, NUMLOCK = 0x90, SCROLLLOCK = 0x91, COMMA = 0xBC, HIFFEN = 0xBD, DOT = 0xBE, BAR = 0xBF, SINGLEQUOTE = 0xD3}
  6924.     local numberkeys = {0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39}
  6925.  
  6926.     if tonumber(key) then
  6927.         return numberkeys[key + 1]
  6928.     end
  6929.     return keys[string.upper(key)]
  6930. end
  6931.  
  6932. function press(keys) -- Working
  6933.     local i = 1
  6934.     while i <= #keys do
  6935.         local key = ''
  6936.         if string.sub(keys, i, i) == '[' then
  6937.             i2 = i + string.find(string.sub(keys, i), ']')
  6938.             key = string.sub(keys, i+1, i2-2)
  6939.             keyevent(keyid(key))
  6940.             i = i2
  6941.         elseif string.sub(keys, i, i) ~= ']' then
  6942.             keyevent(keyid(string.sub(keys, i, i)))
  6943.             i = i + 1
  6944.         end
  6945.     end
  6946. end
  6947.  
  6948. function itemprice(itemname) -- Working
  6949.     return itemcost(itemname)
  6950. end
  6951.  
  6952.  
  6953. function filecontent(filename) -- Working
  6954.     if not fileexists(filename) then
  6955.         return ''
  6956.     end
  6957.     local handler = io.open(filename, 'r')
  6958.     content = handler:read('*a')
  6959.     handler:close()
  6960.     return content
  6961. end
  6962.  
  6963. function filelinescount(filename) -- Working
  6964.     if not fileexists(filename) then
  6965.         return 0
  6966.     end
  6967.     local linecount = 0
  6968.     for line in io.lines(filename) do
  6969.         linecount = linecount + 1
  6970.     end
  6971.     return linecount
  6972. end
  6973.  
  6974. function fileline(filename, linenum) -- Working
  6975.     local linen, linew = 0, ''
  6976.     for line in io.lines(filename) do
  6977.         linen = linen + 1
  6978.         if linen == linenum then
  6979.             linew = line
  6980.         end
  6981.     end
  6982.     return linew
  6983. end
  6984.  
  6985. function filewrite(filename, text) -- Working.
  6986.     local handler = io.open(filename, 'a+')
  6987.     handler:write(text)
  6988.     handler:close()
  6989. end
  6990.  
  6991. function fileexists(filename) -- Working
  6992.     local handler, exists = io.open(filename), false
  6993.     if type(handler) ~= 'nil' then
  6994.         exists = true
  6995.         handler:close()
  6996.     end
  6997.     local handler = nil
  6998.     return exists
  6999. end
  7000.  
  7001. function createfile(filename) -- Working
  7002.     if not fileexists(filename) then
  7003.         clearfile(filename)
  7004.     end
  7005. end
  7006.  
  7007. function execfile(filename)
  7008.     exec(filecontent(filename))
  7009. end
  7010.  
  7011. function filewriteline(filename, text) -- Working.
  7012.     local skip = ''
  7013.     if filelinescount(filename) > 0 then
  7014.         skip = '\n'
  7015.     end
  7016.     local handler = io.open(filename, 'a+')
  7017.     handler:write(skip..text)
  7018.     handler:close()
  7019. end
  7020.  
  7021. function clearfile(filename) -- Working.
  7022.     local handler = io.open(filename, 'w+')
  7023.     handler:close()
  7024. end
  7025.  
  7026. function filerewrite(filename, text)
  7027.     local handler = io.open(filename, 'w+')
  7028.     handler:write(text)
  7029.     handler:close()
  7030. end
  7031.  
  7032. function isfileline(filename, text) -- Working
  7033.     local n = 0
  7034.     if fileexists(filename) then
  7035.         for line in io.lines(filename) do
  7036.             n = n + 1
  7037.             if line == text then
  7038.                 return n
  7039.             end
  7040.         end
  7041.     end
  7042.     return false
  7043. end
  7044.  
  7045. file = {}
  7046. file.content = filecontent
  7047. file.linescount = filelinescount
  7048. file.line = fileline
  7049. file.write = filewrite
  7050. file.exists = fileexists
  7051. file.create = createfile
  7052. file.exec = execfile
  7053. file.writeline = filewriteline
  7054. file.clear = clearfile
  7055. file.rewrite = filerewrite
  7056. file.isline = isfileline
  7057.  
  7058. function exec(execstring) -- Working
  7059.     local func = loadstring(execstring)
  7060.     local arg = {pcall(func)}
  7061.     table.insert(arg, arg[1])
  7062.     table.remove(arg, 1)
  7063.     return table.unpack(arg)
  7064. end
  7065.  
  7066. function vocation() -- Working
  7067.     local voc = 'unknown'
  7068.     local vocs = {
  7069.         mage = 5,
  7070.         paladin = 10,
  7071.         knight = 15
  7072.         }
  7073.  
  7074.     local hpplevel = ($maxhp - 185) / ($level - 8)
  7075.     for k, v in pairs(vocs) do
  7076.         if hpplevel == v then
  7077.             voc = k
  7078.             break
  7079.         end
  7080.     end
  7081.  
  7082.     if voc == 'mage' then
  7083.         local items = {
  7084.             druid = {
  7085.                 rhand   = {3065, 3066, 3067, 3069, 3070, 8082, 8083, 8084},
  7086.                 chest   = {8038, 8041}
  7087.             },
  7088.  
  7089.             sorcerer = {
  7090.                 rhand   = {3071, 3072, 3073, 3074, 3075, 8092, 8093, 8094},
  7091.                 chest   = {8037, 8039, 8040, 8062}
  7092.             }
  7093.         }
  7094.  
  7095.         for k, v in pairs(items) do
  7096.             for p, q in pairs(v) do
  7097.                 local id = exec('return $' .. p .. '.id')
  7098.                 for _, x in ipairs(q) do
  7099.                     if x == id then
  7100.                         return k
  7101.                     end
  7102.                 end
  7103.             end
  7104.         end
  7105.     end
  7106.     return voc
  7107. end
  7108.  
  7109. function maxcap() -- Working
  7110.     local vocs = {
  7111.         unknown = 0,
  7112.         druid = 10,
  7113.         sorcerer = 10,
  7114.         mage = 10,
  7115.         paladin = 20,
  7116.         knight = 30
  7117.     }
  7118.     return vocs[vocation()] * ($level - 8) + 470
  7119. end
  7120.  
  7121. function string.explode(self, sep) -- By Socket, improved by Hardek. Working
  7122.     local result = {}
  7123.     self:gsub("[^".. sep .."*]+", function(s) table.insert(result, (string.gsub(s, "^%s*(.-)%s*$", "%1"))) end)
  7124.     return result
  7125. end
  7126.  
  7127. function sethealrule(rule, hprange, mprange, method, condition, spam) -- Working
  7128.     local settings = {'HealthRange', 'ManaRange', 'HealMethod', 'ExtraCondition', 'SpamRate'}
  7129.     local settingsTo = {((hprange:find('%%') and hprange:find(' %%')) and hprange:gsub('-', ' to ') or hprange:gsub('-', ' to '):gsub('%%', ' %%')):lower(), ((mprange:find('%%') and mprange:find(' %%')) and mprange:gsub('-', ' to ') or mprange:gsub('-', ' to '):gsub('%%', ' %%')):lower(), method:capitalizeall(), ((condition:lower():find('paralyze')) and 'If paralyzed' or ((condition == '') and 'No condition')):capitalize(), ((not spam) and '' or spam:gsub('-', ' to ')):lower()}
  7130.  
  7131.     for i = 1, #settings do
  7132.         setsetting('Healer/HealRules/'..rule..'/'..settings[i], settingsTo[i] or getsetting('Healer/HealRules/'..rule..'/'..settings[i]))
  7133.     end
  7134. end
  7135.  
  7136. function string.capitalize(self) -- Working
  7137.     return string.upper(self:sub(1,1)) .. self:sub(2):lower()
  7138. end
  7139.  
  7140. function string.capitalizeall(self) -- Working
  7141.     local t = string.explode(self, ' ')
  7142.     for i = 1, #t do
  7143.         t[i] = t[i]:capitalize()
  7144.     end
  7145.     return table.concat(t, ' ')
  7146. end
  7147.  
  7148. function bestskill() -- Working
  7149.     local t = {$axe+$axepc/100, {type = 'axe', skill = $axe, skillpc = $axepc}, $club+$clubpc/100, {type = 'club', skill = $club, skillpc = $clubpc}, $sword+$swordpc/100, {type = 'sword', skill = $sword, skillpc = $swordpc}, $distance+$distancepc/100, {type = 'distance', skill = $distance, skillpc = $distancepc}, $fist+$fistpc/100, {type = 'fist', skill = $fist, skillpc = $fistpc}}
  7150.     local j = 0
  7151.     for i = 1, #t, 2 do
  7152.         j = math.max(j, t[i])
  7153.     end
  7154.     return t[table.find2(t, j)+1]
  7155. end
  7156.  
  7157. function weaponskill() -- Working
  7158.     local t = {'axe', {type = 'axe', skill = $axe, skillpc = $axepc}, 'club', {type = 'club', skill = $club, skillpc = $clubpc}, 'sword', {type = 'sword', skill = $sword, skillpc = $swordpc}, {'bow', 'distance weapon'}, {type = 'distance', skill = $distance, skillpc = $distancepc}, 'no weapon', {type = 'fist', skill = $fist, skillpc = $fistpc}, {'rod', 'wand'}, {type = 'magic', skill = $mlevel, skillpc = $mlevelpc}}
  7159.     return t[table.find2(t, findweapontype())+1]
  7160. end
  7161.  
  7162. function table.find2(self, value, arg, notable, argonly) -- Working
  7163.     for i = 1, #self do
  7164.         if not argonly then
  7165.             if self[i] == value then
  7166.                 return i
  7167.             end
  7168.         end
  7169.         if type(self[i]) == 'table' then
  7170.             if arg then
  7171.                 if self[i][arg] == value then
  7172.                     return i
  7173.                 end
  7174.             elseif not notable then
  7175.                 for j = 1, #self[i] do
  7176.                     if self[i][j] == value then
  7177.                         return i, j
  7178.                     end
  7179.                 end
  7180.             end
  7181.         end
  7182.     end
  7183. end
  7184.  
  7185. function exptolvl(a, b) -- Working
  7186.     a = a or $level + 1
  7187.     if b then
  7188.         return exptolvl(b) - exptolvl(a)
  7189.     elseif a then
  7190.         return 50 / 3 * (a ^ 3 - 6 * a ^ 2 + 17 * a - 12)
  7191.     end
  7192. end
  7193.  
  7194. function levelpc() -- Working
  7195.     return math.floor(($exp - exptolvl($level)) * 100 / exptolvl($level, $level + 1))
  7196. end
  7197.  
  7198. function table.random(self, start, finish, count, step) -- Working
  7199.     self = {}
  7200.     step = step or 1
  7201.     count = (count ~= 0 and count) and count or math.floor((finish - start) / step)
  7202.     for i = 1, count do
  7203.         local r = math.random(start, finish)
  7204.         while table.find(self, r) do
  7205.             r = math.random(start, finish)
  7206.         end
  7207.         table.insert(self, r)
  7208.     end
  7209.     return self
  7210. end
  7211.  
  7212. function iscursorin(sx, sy, fx, fy, area) -- working
  7213.     if type(sx) == 'table' then
  7214.         area = true
  7215.         fx = sx.width
  7216.         fy = sx.height
  7217.         sy = sx.y
  7218.         sx = sx.x
  7219.     end
  7220.  
  7221.     if area then
  7222.         fx, fy = sx + fx, sy + fy
  7223.     end
  7224.     if $cursor.x >= sx then
  7225.         if $cursor.x <= fx then
  7226.             if $cursor.y >= sy then
  7227.                 if $cursor.y <= fy then
  7228.                     return true
  7229.                 end
  7230.             end
  7231.         end
  7232.     end
  7233.     return false
  7234. end
  7235.  
  7236. function utcoffset() -- Working
  7237.     local now = os.time()
  7238.     return os.difftime(now, os.time(os.date("!*t", now)) - (os.date('*t').isdst and 3600 or 0))
  7239. end
  7240.  
  7241. function cetoffset() -- Working
  7242.     local now = os.time()
  7243.     return os.difftime(now, os.time(os.date("!*t", now)) - (os.date('*t').isdst and 3600 or 0) + ((os.date('*t').yday > 141 and os.date('*t').yday < 233) and 7200 or 3600))
  7244. end
  7245.  
  7246.  
  7247. function utctime() -- Working
  7248.     return tosec(os.date('%X')) - utcoffset()
  7249. end
  7250.  
  7251.  
  7252. function cettime() -- Working
  7253.     return tosec(os.date('%X')) - cetoffset()
  7254. end
  7255.  
  7256. function timezone() -- Working
  7257.     if utcoffset() then
  7258.         return 'UTC '..utcoffset()/3600
  7259.     end
  7260.     return 'UTC'
  7261. end
  7262.  
  7263. function sstime(world) -- Working
  7264.     world = world:lower()
  7265.     local ssworlds = {
  7266.         8, {'arcania', 'askara', 'aurea', 'berylia', 'celesta', 'furora', 'galana', 'guardia', 'iridia', 'kyra', 'morgana', 'nebula', 'obsidia', 'pandoria', 'refugia', 'saphira', 'selena', 'thoria', 'xerena'},
  7267.         9, {'aldora', 'antica', 'azuera', 'candia', 'danubia', 'elysia', 'eternia', 'harmonia', 'hiberna', 'inferna', 'isara', 'lunara', 'nerana', 'nova', 'olympa', 'premia', 'secura', 'titania', 'valoria'},
  7268.         11, {'astera', 'balera', 'danera', 'elera', 'empera', 'fortera', 'grimera', 'honera', 'jamera', 'keltera', 'lucera', 'luminera', 'malvera', 'menera', 'neptera', 'ocera', 'pythera', 'samera', 'shanera', 'shivera', 'silvera', 'tenebra', 'vinera', 'zanera'},
  7269.         12, {'amera', 'calmera', 'chimera', 'dolera', 'fidera', 'julera', 'libera', 'magera', 'mythera', 'pacera', 'rubera', 'solera', 'trimera', 'unitera', 'xantera'}
  7270.                         }
  7271.     for i = 2, 8, 2 do
  7272.         if table.binaryfind(ssworlds[i], world) then
  7273.             return (ssworlds[i-1] * 3600 - cettime()) % 86400
  7274.         end
  7275.     end
  7276. end
  7277.  
  7278. function time(secs, pattern) -- Working
  7279.     local times = {dd = math.floor(secs / 86400), hh = math.floor(secs / 3600) % 24, mm = math.floor(secs / 60) % 60, ss = secs % 60}
  7280.     if not pattern then
  7281.         if times.dd > 0 then
  7282.             pattern = 'dd:hh:mm:ss'
  7283.         elseif times.hh > 0 then
  7284.             pattern = 'hh:mm:ss'
  7285.         else
  7286.             pattern = 'mm:ss'
  7287.         end
  7288.     end
  7289.     pattern = pattern:lower()
  7290.     for k, v in pairs(times) do
  7291.         pattern = string.gsub(pattern, k, math.format(v, "00"))
  7292.     end
  7293.     return pattern
  7294. end
  7295.  
  7296. function math.format(self, pattern) -- Working
  7297.     local a, b = pattern, tostring(self)
  7298.     local c, d = (a:find("%.")), (b:find("%."))
  7299.     local za, zb = math.max(0, (c or #a + 1) - (d or #b + 1)), math.max(0, (#a - (c or 99999)) - (#b - (d or #b)))
  7300.     local dot = (c and not d) and '.' or ''
  7301.     return string.rep("0", za) .. b .. dot .. string.rep("0", zb)
  7302. end
  7303.  
  7304. function beep() -- Working
  7305.     playsound('monster.wav')
  7306. end
  7307.  
  7308. function sqmWidth() -- Working
  7309.     return ($worldwin.right - $worldwin.left) / 15
  7310. end
  7311.  
  7312. function distto(...) -- Working
  7313.     local arg = {...}
  7314.     local a, b, anyfloor
  7315.     if type(arg[1]) == 'userdata' then
  7316.         a = {x = arg[1].posx, y = arg[1].posy, z = arg[1].posz}
  7317.         if type(arg[2]) == 'userdata' then
  7318.             b = {x = arg[2].posx, y = arg[2].posy, z = arg[2].posz}
  7319.             anyfloor = arg[3]
  7320.         else
  7321.             b = {x = arg[2], y = arg[3], z = arg[4]}
  7322.             anyfloor = arg[5]
  7323.         end
  7324.     else
  7325.         a = {x = arg[1], y = arg[2], z = arg[3]}
  7326.         if type(arg[4]) == 'userdata' then
  7327.             b = {x = arg[4].posx, y = arg[4].posy, z = arg[4].posz}
  7328.             anyfloor = arg[5]
  7329.         else
  7330.             b = {x = arg[4], y = arg[5], z = arg[6]}
  7331.             anyfloor = arg[7]
  7332.         end
  7333.     end
  7334.     return (anyfloor or a.z == b.z) and math.max(math.abs(a.x - b.x), math.abs(a.y - b.y)) or -1
  7335. end
  7336.  
  7337. function string.at(self, n) -- Working
  7338.     return string.sub(self, n, n)
  7339. end
  7340.  
  7341. function string.ends(self, substr) -- Working
  7342.     return string.sub(self, -#substr) == substr
  7343. end
  7344.  
  7345. function string.starts(self, substr) -- Working
  7346.     return string.sub(self, #substr) == substr
  7347. end
  7348.  
  7349. function table.isempty(self) -- Working
  7350.     return next(self) == nil
  7351. end
  7352.  
  7353. function table.size(self) -- Working
  7354.     local i = 0
  7355.     for j in pairs(self) do
  7356.         i = i + 1
  7357.     end
  7358.     return i
  7359. end
  7360.  
  7361. function toyesno(arg) -- Working
  7362.     local returns = {true, 'yes', 'yes', false, 'no', 'no', nil, 'no'}
  7363.     local i = table.find2(returns, arg)
  7364.     if i then
  7365.         return returns[i+1]
  7366.     else
  7367.         return toyesno(arg ~= 0 and arg ~= '')
  7368.     end
  7369. end
  7370.  
  7371. function pm(message, ...) -- Working
  7372.     local players = {...}
  7373.     if #players > 1 then
  7374.         for k, v in ipairs(players) do
  7375.             pm(message, v)
  7376.         end
  7377.     elseif #players == 1 then
  7378.         local player = players[1]
  7379.         if ischannel(player) then
  7380.             say(player, message)
  7381.         else
  7382.             for i = 1, #player-1 do
  7383.                 if ischannel(string.sub(player, 1, i) .. "...") then
  7384.                     say(string.sub(player, 1, i) .. "...", message)
  7385.                     return
  7386.                 end
  7387.             end
  7388.             say('*' .. player .. '* ' .. message)
  7389.         end
  7390.     end
  7391. end
  7392.  
  7393. function sethotkey(hkname, state) -- Working
  7394.     if string.find(hkname, '/') then
  7395.         setsetting(hkname, toyesno(state))
  7396.     else
  7397.         if getsetting('Hotkeys/PersistentList/'..hkname..'/Enabled') then
  7398.             sethotkey('Hotkeys/PersistentList/'..hkname..'/Enabled', state)
  7399.         elseif getsetting('Hotkeys/CavebotList/'..hkname..'/Enabled', state) then
  7400.             sethotkey('Hotkeys/CavebotList/'..hkname..'/Enabled', state)
  7401.         else
  7402.             error('bad argument #1 to \'sethotkey\' (hotkey \'' .. hkname .. '\' couldn\'t be found)')
  7403.         end
  7404.     end
  7405. end
  7406.  
  7407. function getcont(location, bpsonly, index) -- Working
  7408.     local a, b = location or 0, location or 15
  7409.     local backpacks =  {2854, 2865, 2866, 2867, 2868, 2869, 2870, 2871, 2872, 3253, 5801, 5926, 5949, 7342, 8860, 9601, 9602, 9604, 9605, 10202, 10324, 10326, 10327, 10346}
  7410.     local conts = {}
  7411.     for i = a, b do
  7412.         local cont = getcontainer(i)
  7413.         if  cont.isopen and cont.itemcount >= 1 then
  7414.             for k = 1, cont.itemcount do
  7415.                 local item = cont.item[k]
  7416.                 if bpsonly then
  7417.                     if table.find(backpacks, item.id) then
  7418.                         table.insert(conts, item.id)
  7419.                     end
  7420.                 elseif itemproperty(item.id, 4) then
  7421.                     table.insert(conts, item.id)
  7422.                 end
  7423.             end
  7424.         end
  7425.     end
  7426.     if index then
  7427.         return conts[index] or nil
  7428.     else
  7429.         return conts
  7430.     end
  7431. end
  7432.  
  7433. function movewhilemoveable(x, y, z, dx, dy, dz) -- Working
  7434.     local dx, dy, dz = dx or $posx, dy or $posy, dz or $posz
  7435.     local id = topitem(x, y, z).id
  7436.     while not itemproperty(id, 13) do
  7437.         moveitems(id, ground(dx, dy, dz), ground(x, y, z))
  7438.         waitping()
  7439.         id = topitem(x, y, z).id
  7440.     end
  7441. end
  7442.  
  7443. function boatprice(source, dest, post) -- Working. Credits to MeMyselfI
  7444.     local boat_table = {
  7445.         ["ab'dendriel"] = {
  7446.             carlin = 80,
  7447.             edron = 70,
  7448.             thais = 130,
  7449.             venore = 90,
  7450.             yalahar = 160
  7451.         },
  7452.         ankrahmun = {
  7453.             edron = 160,
  7454.             ["liberty bay"] = 90,
  7455.             ["port hope"] = 80,
  7456.             venore = 150,
  7457.             yalahar = 230
  7458.         },
  7459.         carlin = {
  7460.             edron = 110,
  7461.             svargrond = 110,
  7462.             thais = 110,
  7463.             venore = 130,
  7464.             yalahar = 185
  7465.         },
  7466.         darashia = {
  7467.             ["liberty bay"] = 200,
  7468.             ["port hope"] = 180,
  7469.             venore = 60,
  7470.             yalahar = 210
  7471.         },
  7472.         edron = {
  7473.             ankrahmun = 160,
  7474.             carlin = 110,
  7475.             ["liberty bay"] = 170,
  7476.             ["port hope"] = 150,
  7477.             thais = 160,
  7478.             venore = 40
  7479.         },
  7480.         goroma = {
  7481.             ["liberty bay"] = 0
  7482.         },
  7483.         ["liberty bay"] = {
  7484.             darashia = 200,
  7485.             edron = 170,
  7486.             goroma = 500,
  7487.             ["port hope"] = 50,
  7488.             thais = 180,
  7489.             venore = 180,
  7490.             yalahar = 275
  7491.         },
  7492.         ["port hope"] = {
  7493.             darashia = 180,
  7494.             edron = 150,
  7495.             ["liberty bay"] = 50,
  7496.             thais = 160,
  7497.             venore = 160,
  7498.             yalahar = 260
  7499.         },
  7500.         svargrond = {
  7501.             thais = 180,
  7502.             venore = 150
  7503.         },
  7504.         thais = {
  7505.             carlin = 110,
  7506.             edron = 160,
  7507.             ["liberty bay"] = 180,
  7508.             ["port hope"] = 160,
  7509.             svargrond = 180,
  7510.             venore = 170,
  7511.             yalahar = 200
  7512.         },
  7513.         venore = {
  7514.             ankrahmun = 150,
  7515.             carlin = 130,
  7516.             darashia = 60,
  7517.             edron = 40,
  7518.             ["liberty bay"] = 180,
  7519.             ["port hope"] = 160,
  7520.             svargrond = 150,
  7521.             thais = 170,
  7522.             yalahar = 185
  7523.         },
  7524.         yalahar = {
  7525.             ankrahmun = 230,
  7526.             carlin = 185,
  7527.             darashia = 210,
  7528.             ["liberty bay"] = 275,
  7529.             ["port hope"] = 260,
  7530.             thais = 200,
  7531.             venore = 185
  7532.         }
  7533.     }
  7534.  
  7535.     source, dest = source:lower(), dest:lower()
  7536.     local i = boat_table[source]
  7537.     if i then
  7538.         i = i[dest]
  7539.         if i then
  7540.             return i - (post and 10 or 0)
  7541.         end
  7542.         printerror('Can\'t travel to ' .. dest .. ' from ' .. source .. '.')
  7543.         return 0
  7544.     end
  7545.     printerror('Couldn\'t find location ' .. source .. '.')
  7546. end
  7547.  
  7548. function listversion() -- Working
  7549.     return itemid('list version')
  7550. end
  7551.  
  7552. function findgrounditem(id, index) -- Working
  7553.     local items = {}
  7554.     local index = index or 1
  7555.     if type(id) == 'string' then
  7556.         id = itemid(id)
  7557.     end
  7558.     local fx, tx, fy, ty, z = $posx - 7, $posx + 7, $posy - 5, $posy + 5, $posz
  7559.     for y = fy, ty do
  7560.         for x = fx, tx do
  7561.             if topitem(x, y, z).id == id then
  7562.                 table.insert(items, {x, y, z})
  7563.             end
  7564.         end
  7565.     end
  7566.     if #items >= index then
  7567.         return table.unpack(items[index])
  7568.     else
  7569.         return 0, 0, 0
  7570.     end
  7571. end
  7572.  
  7573. function canlevitate(x, y, z) -- Working
  7574.     z = z or $posz
  7575.     local tile = gettile(x, y, z)
  7576.     local c = 0
  7577.     for i = 1, tile.itemcount do
  7578.         local id = tile.item[i].id
  7579.         if itemproperty(id, 25) and not itemproperty(id, 30) then
  7580.             c = c + 1
  7581.         end
  7582.     end
  7583.     return c >= 3
  7584. end
  7585.  
  7586. function findrope(hotkeys) -- Working
  7587.     if itemcount(3003) >= 1 then
  7588.         return 'Rope'
  7589.     elseif itemcount(646) >= 1 then
  7590.         return 'Elvenhair rope'
  7591.     elseif itemcount(9598) >= 1 then
  7592.         return 'Driller'
  7593.     elseif hotkeys then
  7594.         if clientitemhotkey(3003) ~= 'not found' then
  7595.             return 'Rope'
  7596.         elseif clientitemhotkey(646) ~= 'not found' then
  7597.             return 'Elvenhair rope'
  7598.         elseif clientitemhotkey(9598) ~= 'not found' then
  7599.             return 'Driller'
  7600.         end
  7601.     else
  7602.         return nil
  7603.     end
  7604. end
  7605.  
  7606. function findshovel(hotkeys) -- Working
  7607.     if itemcount(3457) >= 1 then
  7608.         return 'Shovel'
  7609.     elseif itemcount(5710) >= 1 then
  7610.         return 'Light shovel'
  7611.     elseif itemcount(9598) >= 1 then
  7612.         return 'Driller'
  7613.     elseif hotkeys then
  7614.         if clientitemhotkey(3457) ~= 'not found' then
  7615.             return 'Shovel'
  7616.         elseif clientitemhotkey(5710) ~= 'not found' then
  7617.             return 'Light shovel'
  7618.         elseif clientitemhotkey(9598) ~= 'not found' then
  7619.             return 'Driller'
  7620.         end
  7621.     else
  7622.         return nil
  7623.     end
  7624. end
  7625.  
  7626. function getpath(setting, path, entry) -- Working
  7627.     if getsetting(setting) then
  7628.         return setting
  7629.     end
  7630.  
  7631.     if entry then
  7632.         local name = getsetting(entry, '_name')
  7633.         if string.ends(path .. name, setting) then
  7634.             return path .. name
  7635.         elseif #name > 0 then
  7636.             foreach settingsentry e (path .. name) do
  7637.                 local s = getpath(setting, path .. name .. '/', e)
  7638.                 if s then
  7639.                     return s
  7640.                 end
  7641.             end
  7642.         end
  7643.     else
  7644.         for _, v in ipairs({'Alerts', 'Cavebot', 'Healer', 'Hotkeys', 'Hud', 'Input', 'Targeting'}) do
  7645.             foreach settingsentry e v do
  7646.                 local s = getpath(setting, v .. '/', e)
  7647.                 if s then
  7648.                     return s
  7649.                 end
  7650.             end
  7651.         end
  7652.     end
  7653.     return nil
  7654. end
  7655.  
  7656. function set(setting, value, updgui) -- Working
  7657.     updgui = updgui or true
  7658.     local path = getpath(setting)
  7659.     if path then
  7660.         setsetting(path, value, updgui)
  7661.     else
  7662.         error('bad argument #1 to \'set\' (the specified setting does not exist)')
  7663.     end
  7664. end
  7665.  
  7666. function get(setting) -- Working
  7667.     local path = getpath(setting) or ''
  7668.     return getsetting(path, value, updgui)
  7669. end
  7670.  
  7671. function string.sub2(self, i, l) -- Working
  7672.     if l then
  7673.         return string.sub(self, i, i + l - math.min(1, i))
  7674.     else
  7675.         return string.sub(self, i)
  7676.     end
  7677. end
  7678.  
  7679. function ground(...) -- Working
  7680.     local arg = {...}
  7681.     if type(arg[1]) == 'table' then
  7682.         arg = {arg.x or arg.posx or $posx, arg.y or arg.posy or $posy, arg.z or arg.posz or $posz}
  7683.     elseif type(arg[1]) == 'userdata' then
  7684.         arg = {arg.posx, arg.posy, arg.posz}
  7685.     else
  7686.         arg = {arg[1] or $posx, arg[2] or $posy, arg[3] or $posz}
  7687.     end
  7688.     return "ground " .. table.concat(arg,  " ")
  7689. end
  7690.  
  7691. border = "border"
  7692. shadow = "shadow"
  7693. _ADDTEXT = _ADDTEXT or addtext
  7694. function addtext(...)
  7695.     local arg = {...}
  7696.     arg[2], arg[3] = arg[2] or 0, arg[3] or 0
  7697.     if arg[4] then
  7698.         local o = arg[7] or 1
  7699.         setfontcolor(arg[6] or 0x000000)
  7700.         _ADDTEXT(arg[1], arg[2] - o, arg[3] + o)
  7701.         if arg[4] == border then
  7702.             _ADDTEXT(arg[1], arg[2] + o, arg[3] - o)
  7703.             _ADDTEXT(arg[1], arg[2] + o, arg[3] + o)
  7704.             _ADDTEXT(arg[1], arg[2] - o, arg[3] - o)
  7705.             _ADDTEXT(arg[1], arg[2] - o, arg[3])
  7706.             _ADDTEXT(arg[1], arg[2] + o, arg[3])
  7707.             _ADDTEXT(arg[1], arg[2], arg[3] + o)
  7708.             _ADDTEXT(arg[1], arg[2], arg[3] - o)
  7709.         end
  7710.         setfontcolor(arg[5] or 0xFFFFFF)
  7711.     end
  7712.     _ADDTEXT(arg[1], arg[2], arg[3])
  7713. end
  7714.  
  7715.  
  7716. function isBetween(v1, v2, x, y, w, h)
  7717.     if v1 >= x then
  7718.         if v1 <= x + w then
  7719.             if v2 >= y then
  7720.                 if v2 <= y + h then
  7721.                     return true
  7722.                 end
  7723.             end
  7724.         end
  7725.     end
  7726.     return false
  7727. end
  7728.  
  7729. function isadmin()
  7730.     return (pcall(
  7731.         function()
  7732.             local handler = io.open('test.txt', 'w+')
  7733.             handler:write('test')
  7734.             handler:close()
  7735.         end
  7736.     ))
  7737. end
  7738.  
  7739.  
  7740.  
  7741. local Default = {}
  7742. Default.Button = {}
  7743. Default.Button.Size = {x = 50, y = 20}
  7744. Default.Button.Spacing = {x = 6, y = 6}
  7745. Default.Button.Position = {x = 0, y = 0}
  7746. Default.Button.Action = function() end
  7747. Default.Button.Text = "Button"
  7748.  
  7749.  
  7750. ------------------------------------------------------------------------------
  7751. --                Oriented Object Programming - First Try                   --
  7752. ------------------------------------------------------------------------------
  7753.  
  7754. Align = {
  7755.     left = "left",
  7756.     right = "right",
  7757.     bot = "bottom",
  7758.     top = "top"
  7759.     }
  7760.  
  7761.  
  7762. Listbox = {}
  7763.  
  7764. -- Creates the object
  7765. function Listbox:new(obj)
  7766.     obj = obj or {}
  7767.     if not obj.lines then
  7768.         obj.lines = {}
  7769.     end
  7770.     if not obj.defaultColor then
  7771.         obj.defaultColor = 0xFFFFFF
  7772.     end
  7773.     if not obj.maxIndex then
  7774.         obj.maxIndex = 5
  7775.     end
  7776.     if not obj.verAlign then
  7777.         obj.verAlign = Align.bot
  7778.     end
  7779.     if not obj.horAlign then
  7780.         obj.horAlign = Align.left
  7781.     end
  7782.     if not obj.spacing then
  7783.         obj.spacing = 13
  7784.     end
  7785.     return setmetatable(obj, {__index = self})
  7786. end
  7787.  
  7788. function Listbox:setDefaultColor(color)
  7789.     self.defaultColor = color
  7790. end
  7791.  
  7792. function Listbox:getDefaultColor()
  7793.     return self.defaultColor
  7794. end
  7795.  
  7796. function Listbox:setMaxIndex(maxIndex)
  7797.     self.maxIndex = maxIndex
  7798. end
  7799.  
  7800. function Listbox:getMaxIndex()
  7801.     return self.maxIndex
  7802. end
  7803.  
  7804. function Listbox:setAlignment(...)
  7805.     local arg = {...}
  7806.     if not select(2, self:getAlignment(arg[1]:sub(1, 3))) then
  7807.         self[arg[1]:sub(1, 3) .. "Align"] = arg[2]
  7808.     else
  7809.         self.horAlign, self.verAlign = arg[1], arg[2]
  7810.     end
  7811. end
  7812.  
  7813. function Listbox:getAlignment(way)
  7814.     way = (way or "abc"):sub(1, 3)
  7815.     if way == "hor" then
  7816.         return self.horAlign
  7817.     elseif way == "ver" then
  7818.         return self.verAlign
  7819.     else
  7820.         return self.horAlign, self.verAlign
  7821.     end
  7822. end
  7823.  
  7824. function Listbox:setLineSpacing(spacing)
  7825.     self.spacing = spacing
  7826. end
  7827.  
  7828. function Listbox:getLineSpacing()
  7829.     return self.spacing
  7830. end
  7831.  
  7832. function Listbox:getLine(index)
  7833.     return self.lines[index]
  7834. end
  7835.  
  7836. function Listbox:size()
  7837.     return #self.lines
  7838. end
  7839.  
  7840. function Listbox:checkSize()
  7841.     local maxindex = self:getMaxIndex()
  7842.     while self:size() > maxindex do
  7843.         self:rmvLine()
  7844.     end
  7845. end
  7846.  
  7847. function Listbox:addLine(value, color, index)
  7848.     table.insert(self.lines, index or 1, {text = value, color = color})
  7849.     self:checkSize()
  7850. end
  7851.  
  7852. function Listbox:rmvLine(index)
  7853.     if index then
  7854.         table.remove(self.lines, index)
  7855.     else
  7856.         table.remove(self.lines)
  7857.     end
  7858. end
  7859.  
  7860. function Listbox:setPosition(x, y)
  7861.     local hor, ver = self:getAlignment()
  7862.     local size, spac = self:size(), self:getLineSpacing()
  7863.     if ver == Align.bot then
  7864.         y = y - (size * spac)
  7865.     end
  7866.     local Align = {"left", "right"}
  7867.     setjustify(Align[math.abs(table.find(Align, hor) - 2) + 1])
  7868.     setposition(x, y)
  7869. end
  7870.  
  7871. function Listbox:draw()
  7872.     local size = self:size()
  7873.     local maxindex = self:getMaxIndex()
  7874.     local spacing = self:getLineSpacing()
  7875.     local color = self:getDefaultColor()
  7876.     if size > 0 then
  7877.         for i = 1, size do
  7878.             local line = self:getLine(i)
  7879.             setfontcolor(line.color or color)
  7880.             addtext(line.text, 0, (i - 1) * spacing)
  7881.         end
  7882.     end
  7883. end
  7884.  
  7885. ------------------------------------------------------------------------------
  7886. --                Oriented Object Programming - Second Try                  --
  7887. ------------------------------------------------------------------------------
  7888.  
  7889. State = {
  7890.     Released = 0,
  7891.     Pressed = 1
  7892. }
  7893.  
  7894. Button = {}
  7895.  
  7896. -- Object creator
  7897. function Button:new(obj)
  7898.     obj = obj or {}
  7899.  
  7900.     -- Checks for non-defined values
  7901.     obj.Size = obj.Size or Default.Button.Size
  7902.     obj.Spacing = obj.Spacing or Default.Button.Spacing
  7903.     obj.Position = obj.Position or Default.Button.Position
  7904.     obj.Action = obj.Action or Default.Button.Action
  7905.     obj.Text = obj.Text or Default.Button.Text
  7906.  
  7907.     return setmetatable(obj, {__index = self})
  7908. end
  7909.  
  7910. -- Pressed or Not
  7911. Button.State = 0
  7912. Button.AutoSize = true
  7913.  
  7914. function Button:setText(t)
  7915.     self.Text = t
  7916.     if self.AutoSize then
  7917.         local charsWidth = {
  7918.             [" "] = 3,
  7919.             ["!"] = 3,
  7920.             ['"'] = 6,
  7921.             ["#"] = 9,
  7922.             ["$"] = 7,
  7923.             ["%"] = 12,
  7924.             ["&"] = 9,
  7925.             ["'"] = 3,
  7926.             ["("] = 5,
  7927.             [")"] = 5,
  7928.             ["*"] = 6,
  7929.             [","] = 4,
  7930.             ["-"] = 5,
  7931.             ["."] = 3,
  7932.             ["/"] = 6,
  7933.             ["0"] = 7,
  7934.             ["1"] = 7,
  7935.             ["2"] = 7,
  7936.             ["3"] = 7,
  7937.             ["4"] = 7,
  7938.             ["5"] = 7,
  7939.             ["6"] = 7,
  7940.             ["7"] = 7,
  7941.             ["8"] = 7,
  7942.             ["9"] = 7,
  7943.             [":"] = 3,
  7944.             [";"] = 3,
  7945.             ["<"] = 9,
  7946.             ["="] = 9,
  7947.             [">"] = 9,
  7948.             ["?"] = 6,
  7949.             ["@"] = 10,
  7950.  
  7951.             ["A"] = 9,
  7952.             ["B"] = 7,
  7953.             ["C"] = 7,
  7954.             ["D"] = 8,
  7955.             ["E"] = 6,
  7956.             ["F"] = 6,
  7957.             ["G"] = 8,
  7958.             ["H"] = 8,
  7959.             ["I"] = 5,
  7960.             ["J"] = 6,
  7961.             ["K"] = 7,
  7962.             ["L"] = 6,
  7963.             ["M"] = 10,
  7964.             ["N"] = 7,
  7965.             ["O"] = 8,
  7966.             ["P"] = 7,
  7967.             ["Q"] = 8,
  7968.             ["R"] = 8,
  7969.             ["S"] = 7,
  7970.             ["T"] = 7,
  7971.             ["U"] = 8,
  7972.             ["V"] = 7,
  7973.             ["X"] = 7,
  7974.             ["W"] = 11,
  7975.             ["Y"] = 7,
  7976.             ["Z"] = 7,
  7977.  
  7978.             ["["] = 5,
  7979.             ["\\"] = 6,
  7980.             ["]"] = 5,
  7981.             ["^"] = 9,
  7982.             ["_"] = 7,
  7983.             ["`"] = 6,
  7984.  
  7985.             ["a"] = 7,
  7986.             ["b"] = 7,
  7987.             ["c"] = 6,
  7988.             ["d"] = 7,
  7989.             ["e"] = 7,
  7990.             ["f"] = 4,
  7991.             ["g"] = 7,
  7992.             ["h"] = 7,
  7993.             ["i"] = 3,
  7994.             ["j"] = 4,
  7995.             ["k"] = 7,
  7996.             ["l"] = 3,
  7997.             ["m"] = 11,
  7998.             ["n"] = 7,
  7999.             ["o"] = 7,
  8000.             ["p"] = 7,
  8001.             ["q"] = 7,
  8002.             ["r"] = 5,
  8003.             ["s"] = 6,
  8004.             ["t"] = 5,
  8005.             ["u"] = 7,
  8006.             ["v"] = 7,
  8007.             ["x"] = 7,
  8008.             ["w"] = 9,
  8009.             ["y"] = 7,
  8010.             ["z"] = 6,
  8011.  
  8012.             ["{"] = 7,
  8013.             ["|"] = 7,
  8014.             ["}"] = 7,
  8015.             ["~"] = 9,
  8016.         }
  8017.  
  8018.         local w = self.Spacing.x * 2
  8019.         for i = 1, #t do
  8020.             w = w + (charsWidth[string.sub(t, i, i)] or 0)
  8021.         end
  8022.         self:setSize(w, 8 + self.Spacing.y * 2)
  8023.     end
  8024. end
  8025.  
  8026. function Button:getText()
  8027.     return self.Text
  8028. end
  8029.  
  8030. function Button:setSize(x, y)
  8031.     self.Size.x = x
  8032.     self.Size.y = y
  8033. end
  8034.  
  8035. function Button:getSize()
  8036.     return self.Size
  8037. end
  8038.  
  8039. function Button:setSpacing(x, y)
  8040.     self.Spacing.x = x
  8041.     self.Spacing.y = y
  8042.     if self.AutoSize then
  8043.         self:setText(self.Text)
  8044.     end
  8045. end
  8046.  
  8047. function Button:getSpacing()
  8048.     return self.Spacing
  8049. end
  8050.  
  8051. function Button:setState(state)
  8052.     self.State = state
  8053. end
  8054.  
  8055. function Button:getState()
  8056.     return self.State
  8057. end
  8058.  
  8059. function Button:setPosition(x, y)
  8060.     self.Position.x = x
  8061.     self.Position.y = y
  8062. end
  8063.  
  8064. function Button:getPosition()
  8065.     return self.Position
  8066. end
  8067.  
  8068. function Button:setEvent(f)
  8069.     self.Action = f
  8070. end
  8071.  
  8072. function Button:runEvent()
  8073.     self.Action()
  8074. end
  8075.  
  8076. function Button:setAutoSize(v)
  8077.     self.AutoSize = v
  8078.     if v then
  8079.         self:setText(self.Text)
  8080.     end
  8081. end
  8082.  
  8083. function Button:draw()
  8084.     -- Sets predefined options
  8085.     setfontweight(255)
  8086.     setbordercolor(0x000000)
  8087.     setfillstyle("image", "Button.png")
  8088.     setfontstyle("Tahoma", 8, 0xDFDFDF)
  8089.  
  8090.     -- Sets some variables for later use
  8091.     local colors = {0x6D6D6D, 0x2A2A2A, 0x6D6D6D}
  8092.     local Pos = self.Position
  8093.     local Size = self.Size
  8094.  
  8095.     -- Draws the button shape
  8096.     addshape("rect", Pos.x, Pos.y, Size.x, Size.y)
  8097.  
  8098.     -- Draws upper and left borders
  8099.     setbordercolor(colors[self.State +1])
  8100.     addshape("rect", Pos.x + 1, Pos.y, Size.x - 1, -1)
  8101.     addshape("rect", Pos.x, Pos.y, -1, Size.y)
  8102.  
  8103.     -- Draws bottom and right borders
  8104.     setbordercolor(colors[self.State +2])
  8105.     addshape("rect", Pos.x + 1, Pos.y + Size.y + 1, Size.x - 1, -1)
  8106.     addshape("rect", Pos.x + Size.x + 1, Pos.y, -1, Size.y)
  8107.  
  8108.     -- Adds the text
  8109.     addtext(self.Text, Pos.x + self.Spacing.x + self.State, Pos.y + self.Spacing.y + self.State)
  8110. end
  8111.  
  8112.  
  8113.  
  8114. ------------------------------Hardek.lua---------------------------------
  8115.  
  8116. -- Hardek's neobot library 0.9.6
  8117. print('Hardek Library Version: 0.9.6')
  8118.  
  8119. function waitping(base)
  8120.     local base = base or 200
  8121.     if ping == 0 then ping = base end
  8122.     wait(2 * ping, 4 * ping)
  8123. end
  8124.  
  8125. function timeleft(t, ctime)
  8126.     local ctime = ctime or currenttime()
  8127.     return tosec(t) - tosec(ctime)
  8128. end
  8129.  
  8130. function depositall()
  8131.     npctalk('hi', 'deposit all', 'yes')
  8132. end
  8133.  
  8134. function withdraw(amount, npc, sayhi)
  8135.     if not amount or amount == 0 then
  8136.         return true
  8137.     end
  8138.  
  8139.     if sayhi == true then
  8140.         npctalk('hi', 'withdraw ' .. amount, 'yes')
  8141.     else
  8142.         npctalk('withdraw ' .. amount, 'yes')
  8143.     end
  8144.  
  8145.     waitping()
  8146.     foreach newmessage m do
  8147.         if m.content == 'There is not enough gold on your account.' then
  8148.             if (not npc) or (npc == '') or (m.sender == npc) then
  8149.                 return false
  8150.             end
  8151.         end
  8152.     end
  8153.  
  8154.     return true
  8155. end
  8156.  
  8157. function tryexec(cmd, x, y, z, maxtries)
  8158.     local tries = 0
  8159.     maxtries = maxtries or 5
  8160.  
  8161.     while tries <= maxtries do
  8162.         if $posx ~= x or $posy ~= y or $posz ~= z then
  8163.             moveto(x, y, z)
  8164.             tries = tries + 1
  8165.             waitping()
  8166.         else
  8167.             exec(cmd)
  8168.             return true
  8169.         end
  8170.     end
  8171.  
  8172.     return false
  8173. end
  8174.  
  8175. function opendepot()
  8176.     local wtp = getsetting('Cavebot/Pathfinding/WalkThroughPlayers')
  8177.     if wtp == 'yes' then setsetting('Cavebot/Pathfinding/WalkThroughPlayers', 'no') end
  8178.  
  8179.     reachgrounditem('depot') waitping()
  8180.     openitem('depot') waitping()
  8181.  
  8182.     setsetting('Cavebot/Pathfinding/WalkThroughPlayers', wtp)
  8183. end
  8184.  
  8185. function movetoinsist(x, y, z, maxtries)
  8186.     local tries = 0
  8187.     maxtries = maxtries or 5
  8188.  
  8189.     while tries <= maxtries and $posx ~= x and $posy ~= y do
  8190.         tries = tries + 1
  8191.         if $posz ~= z then return false end
  8192.         moveto(x, y, z)
  8193.         waitping()
  8194.     end
  8195.  
  8196.     return true
  8197. end
  8198.  
  8199. function refillsofts()
  8200.     local quit = false
  8201.     npctalk('hi')
  8202.     while not quit and itemcount('worn soft boots') > 0 do
  8203.         npctalk('repair', 'yes')
  8204.         wait(2000, 3000)
  8205.         foreach newmessage m do
  8206.             if m.content == 'At last, someone poorer than me.' then
  8207.                 if (not npc) or (m.sender == 'Aldo') then
  8208.                     if not (movetoinsist(33019, 32053, 6) and
  8209.                         withdraw(10000, 'Rokyn', true) and
  8210.                         movetoinsist(32953, 32108, 6)) then
  8211.                         quit = true
  8212.                     else
  8213.                         npcsay('hi')
  8214.                     end
  8215.                 end
  8216.             end
  8217.         end
  8218.     end
  8219. end
  8220.  
  8221. function __loop_open(container, ignore, maxtries)
  8222.     if type(container) == 'string' then container = container:lower() end
  8223.     ignore = ignore:lower()
  8224.     maxtries = maxtries or 5
  8225.     if container == ignore then return (windowcount(container) ~= 0) end
  8226.  
  8227.     local countbefore = windowcount()
  8228.     local tries = 0
  8229.     while (countbefore == windowcount()) and windowcount(container) == 0 and tries <= maxtries do
  8230.         if tries == maxtries then return false end
  8231.         openitem(container, 'Locker', true)
  8232.         waitping()
  8233.         tries = tries + 1
  8234.     end
  8235.  
  8236.     return true
  8237. end
  8238.  
  8239. function __dp_item(item, from, container, container_id)
  8240.     local continue = true
  8241.  
  8242.     while continue and itemcount(item, from) > 0 do
  8243.         if emptycount(container_id) == 0 then
  8244.             continue = (itemcount(container) > 0)
  8245.             if continue then
  8246.                 openitem(container, container_id)
  8247.                 waitping()
  8248.             end
  8249.         else
  8250.             moveitems(item, container_id, from)
  8251.             waitping()
  8252.         end
  8253.     end
  8254. end
  8255.  
  8256. function deposititems(dest, stack, from, open, ...)
  8257.     local items = {...}
  8258.     if type(items[1]) == 'table' then items = items[1] end
  8259.     if open and windowcount('locker') == 0 then opendepot() waitping() end
  8260.     dest = dest or 'locker'
  8261.     stack = stack or 'locker'
  8262.     if type(from) ~= 'table' then from = {from} end
  8263.     if type(dest) == 'string' then dest = dest:lower() end
  8264.     if type(stack) == 'string' then stack = stack:lower() end
  8265.  
  8266.     if (not __loop_open(stack, 'locker')) or (not __loop_open(dest, 'locker')) then return false end
  8267.  
  8268.     destd = windowcount() - 1
  8269.     if stack == dest then stackd = destd else stackd = destd - 1 end
  8270.  
  8271.     for i = 1, #items do
  8272.         if itemproperty(items[i], ITEM_STACKABLE) then
  8273.             for j = 1, #from do
  8274.                 __dp_item(items[i], from[j], stack, stackd)
  8275.             end
  8276.         end
  8277.     end
  8278.  
  8279.     for i = 1, #items do
  8280.         if not itemproperty(items[i], ITEM_STACKABLE) then
  8281.             for j = 1, #from do
  8282.                 __dp_item(items[i], from[j], dest, destd)
  8283.             end
  8284.         end
  8285.     end
  8286. end
  8287.  
  8288. function dropitemsex(cap, ...)
  8289.     local cap = cap or 250
  8290.     local drop = {...}
  8291.  
  8292.     if $cap < cap then
  8293.         for i = 1, #drop do
  8294.             while $cap < cap and itemcount(drop[i]) > 0 do
  8295.                 local count = math.ceil((cap - $cap) / itemweight(drop[i]))
  8296.                 moveitems(itemid(drop[i]), 'ground', '', count)
  8297.             end
  8298.         end
  8299.     end
  8300. end
  8301.  
  8302. function dontlist()
  8303.     listas('dontlist')
  8304. end
  8305.  
  8306. function goback()
  8307.     gotolabel(0)
  8308. end
  8309.  
  8310. function creatureinfo(creaturename)
  8311.     if creaturename == '' then return nil end
  8312.     return creatures_table[table.binaryfind(creatures_table,creaturename:lower(),'name')]
  8313. end
  8314.  
  8315. function creaturemaxhp(creaturename)
  8316.     if creaturename == '' then return 0 end
  8317.     local cre = creatureinfo(creaturename)
  8318.     if cre then return cre.hp end
  8319.     printerror('Monster: '..creaturename..' not found')
  8320.     return 0
  8321. end
  8322.  
  8323. function creaturehp(creaturename)
  8324.     if creaturename == '' then return 0 end
  8325.     if type(creaturename) ~= 'userdata' then
  8326.         creaturename = findcreature(creaturename)
  8327.     end
  8328.     local cre = creaturename
  8329.     local creinfo = creatureinfo(cre.name)
  8330.     if not creinfo then
  8331.         printerror('Monster: '.. cre.name ..' not found')
  8332.         return 0
  8333.     end
  8334.     return creinfo.hp*100/cre.hppc
  8335. end
  8336.  
  8337. function creatureexp(creaturename)
  8338.     if creaturename == '' then return 0 end
  8339.     local cre = creatureinfo(creaturename)
  8340.     if cre then return cre.exp end
  8341.     printerror('Monster: '..creaturename..' not found')
  8342.     return 0
  8343. end
  8344.  
  8345. function expratio(creaturename)
  8346.     if creaturename == '' then return 0 end
  8347.     local cre = creatureinfo(creaturename)
  8348.     if cre then return cre.ratio end
  8349.     printerror('Monster: '..creaturename..' not found')
  8350.     return 0
  8351. end
  8352.  
  8353. function maxdamage(creaturename)
  8354.     if creaturename == '' then return 0 end
  8355.     if creaturename then
  8356.         local cre = creatureinfo(creaturename)
  8357.         if cre then return cre.maxdmg end
  8358.         printerror('Monster: '..creaturename..' not found')
  8359.         return 0
  8360.     else
  8361.         local total = 0
  8362.         foreach creature c "ms" do
  8363.             total = total + maxdamage(c.name)
  8364.         end
  8365.         return total
  8366.     end
  8367. end
  8368.  
  8369. function getelementword(element)
  8370.     local spells = {physical = 'moe ico', holy = 'san', death = 'mort', fire = 'flam', ice = 'frigo', energy = 'vis', earth = 'tera'}
  8371.     if spells[element] then return spells[element] end
  8372.     printerror('Element: '..element..' not found')
  8373.     return nil
  8374. end
  8375.  
  8376. function bestelement(creaturename, strongonly)
  8377.     if creaturename == '' then return nil end
  8378.     local cre = creatureinfo(creaturename)
  8379.     local voc = vocation()
  8380.     strongonly = strongonly or false
  8381.     if voc == 'knight' then
  8382.         return 'physical', cre.physicalmod
  8383.     elseif voc == 'paladin' then
  8384.         if cre.physicalmod > cre.holymod then
  8385.             return 'physical', cre.physicalmod
  8386.         else
  8387.             return 'holy', cre.holymod
  8388.         end
  8389.     elseif voc == 'sorcerer' then
  8390.         local best = ''
  8391.         local max = 0
  8392.         local elements = {}
  8393.         if strongonly then
  8394.             elements = {'energy', 'fire'}
  8395.         else
  8396.             elements = {'energy', 'fire', 'ice', 'earth', 'death'}
  8397.         end
  8398.         for i = 1, #elements do
  8399.             if cre[elements[i]..'mod'] > max then
  8400.                 max = cre[elements[i]..'mod']
  8401.                 best = elements[i]
  8402.             end
  8403.         end
  8404.  
  8405.         return best, max
  8406.     elseif voc == 'druid' then
  8407.         local best = ''
  8408.         local max = 0
  8409.         local elements = {}
  8410.         if strongonly then
  8411.             elements = {'ice', 'earth'}
  8412.         else
  8413.             elements = {'energy', 'fire', 'ice', 'earth', 'physical'}
  8414.         end
  8415.         for i = 1, #elements do
  8416.             if cre[elements[i]..'mod'] > max then
  8417.                 max = cre[elements[i]..'mod']
  8418.                 best = elements[i]
  8419.             end
  8420.         end
  8421.  
  8422.         return best, max
  8423.     elseif voc == 'mage' then
  8424.         local best = ''
  8425.         local max = 0
  8426.         local elements = {'ice', 'earth', 'energy', 'fire'}
  8427.         for i = 1, #elements do
  8428.             if cre[elements[i]..'mod'] > max then
  8429.                 max = cre[elements[i]..'mod']
  8430.                 best = elements[i]
  8431.             end
  8432.         end
  8433.  
  8434.         return best, max
  8435.     end
  8436.  
  8437.     if cre then return cre.bestspell end
  8438.     printerror('Monster: '..creaturename..' not found')
  8439.     return nil
  8440. end
  8441.  
  8442. function beststrike(creaturename)
  8443.     if creaturename == '' then return nil end
  8444.     return 'exori '..getelementword(bestelement(creaturename, false))
  8445. end
  8446.  
  8447. function beststrongstrike(creaturename)
  8448.     if creaturename == '' then return nil end
  8449.     return 'exori gran '..getelementword(bestelement(creaturename, true))
  8450. end
  8451.  
  8452. function bestspell(creaturename)
  8453.     return beststrike(creaturename)
  8454. end
  8455.  
  8456. function buyitemstocap(itemname, cap)
  8457.     local tries = 0
  8458.     local amount = math.floor(($cap - cap) / itemweight(itemname))
  8459.     local maxtries = maxtries or (2 * amount / 100)
  8460.  
  8461.     if not $tradeopen then opentrade() end
  8462.     while $cap > cap and tries <= maxtries do
  8463.         count = itemcount(itemname)
  8464.         amount = math.floor(($cap - cap) / itemweight(itemname)) % 100
  8465.         if amount == 0 then amount = 100 end
  8466.         buyitems(itemname, amount)
  8467.         waitping()
  8468.         tries = tries + 1
  8469.     end
  8470. end
  8471.  
  8472. function itemscosttocap(itemname, cap)
  8473.     local item = iteminfo(itemname)
  8474.     if item then
  8475.         return item.npcprice * math.floor((($cap - cap) / item.weight))
  8476.     end
  8477.     printerror('Item: '..itemname..' not found')
  8478.     return 0
  8479. end
  8480.  
  8481. function trapped()
  8482.         for i = -2, 2 do
  8483.             for j = -2, 2 do
  8484.                 local cx = $posx + i
  8485.                 local cy = $posy + j
  8486.                 if tilereachable(cx, cy, $posz) then return false end
  8487.             end
  8488.         end
  8489.  
  8490.     return true
  8491. end
  8492.  
  8493. function euclideandist(sx, sy, dx, dy)
  8494.     return math.sqrt(math.pow(dx - sx, 2) + math.pow(dy - sy, 2))
  8495. end
  8496.  
  8497. function distto(sx, sy, dx, dy)
  8498.     local distx = math.abs(sx - dx)
  8499.     local disty = math.abs(sy - dy)
  8500.     if distx > disty then
  8501.         return distx
  8502.     else
  8503.         return disty
  8504.     end
  8505. end
  8506.  
  8507. function leavetrap(spell)
  8508.     spell = spell or 'none'
  8509.     local cr = nil
  8510.     local distmin = 100
  8511.     local sp = ''
  8512.     local cb = $cavebot
  8513.  
  8514.     if cb and trapped() then setcavebot('off') end
  8515.     while trapped() do
  8516.         wait(1000)
  8517.         foreach creature c "ms" do
  8518.             if c.dist == 1 then
  8519.                 if cb then
  8520.                     if not cr then cr = c end
  8521.                     local dist = distto($wptx, $wpty, c.posx, c.posy)
  8522.                     if dist < distmin then
  8523.                         distmin = dist
  8524.                         cr = c
  8525.                     end
  8526.                 else
  8527.                     cr = c
  8528.                     break
  8529.                 end
  8530.             end
  8531.         end
  8532.         attack(cr)
  8533.         if spell ~= 'none' then
  8534.             if spell == 'strike' then sp = bestspell(cr.name) else sp = spell end
  8535.             cast(sp)
  8536.         end
  8537.     end
  8538.     if cb then setcavebot('on') end
  8539. end
  8540.  
  8541. function getplayerskill() -- credits for sirmate on this one
  8542.     local weaponType = findweapontype()
  8543.     local playerVocation = vocation()
  8544.     if (playerVocation == 'knight') then
  8545.         if (weaponType == 'club') then
  8546.             return {$club, $clubpc}
  8547.         elseif (weaponType == 'sword') then
  8548.             return {$sword, $swordpc}
  8549.         elseif (weaponType == 'axe') then
  8550.             return {$axe, $axepc}
  8551.         end
  8552.     elseif (playerVocation == 'paladin') then
  8553.         return {$distance, $distancepc}
  8554.     elseif (playerVocation == 'mage' or playerVocation == 'druid' or playerVocation == 'sorcerer') then
  8555.         if ($club >= $sword and $axe) then
  8556.             return {$club, $clubpc}
  8557.         elseif ($sword >= $club and $axe) then
  8558.             return {$sword, $swordpc}
  8559.         elseif ($axe >= $club and $sword) then
  8560.             return {$axe, $axepc}
  8561.         end
  8562.     end
  8563. end
  8564.  
  8565. function spelldamage(spell, level, mlevel, skill)
  8566.     level = level or $level
  8567.     mlevel = mlevel or $mlevel
  8568.     skill = skill or getplayerskill()[1]
  8569.     local sp = spell:gsub(' ', '_')
  8570.     if not spellformulas[sp] then
  8571.         printerror('Spell: '..spell..' not found.')
  8572.         return nil
  8573.     end
  8574.     return spellformulas[sp](level, mlevel, skill)
  8575. end
  8576.  
  8577.  
  8578. -- information tables
  8579.  
  8580. spellformulas = {
  8581.     beserk              = function(a, b, c) return {((a + b) * 0.5 + (c / 5)), ((a + b) * 1.5 + (c / 5))} end,
  8582.     whirlwind_throw     = function(a, b, c) return {(a + b) / 3 + c / 5, a + b + c / 5} end,
  8583.     fierce_beserk       = function(a, b, c) return {((a + b * 2) * 1.1 + (c / 5)), ((a + b * 2) * 3 + (c / 5))} end,
  8584.     etheral_spear       = function(a, b) return {(a + 25) / 3 + b / 5, (a + 25 + b / 5)} end,
  8585.     strike              = function(l, m) return {0.2 * l + 1.403 * m + 08, 0.2 * l + 2.203 * m + 13} end,
  8586.     divine_missile      = function(l, m) return {0.2 * l + 1.790 * m + 11, 0.2 * l + 3.000 * m + 18} end,
  8587.     ice_wave            = function(l, m) return {0.2 * l + 0.810 * m + 04, 0.2 * l + 2.000 * m + 12} end,
  8588.     fire_wave           = function(l, m) return {0.2 * l + 1.250 * m + 04, 0.2 * l + 2.000 * m + 12} end,
  8589.     light_magic_missile = function(l, m) return {0.2 * l + 0.400 * m + 02, 0.2 * l + 0.810 * m + 04} end,
  8590.     heavy_magic_missile = function(l, m) return {0.2 * l + 0.810 * m + 04, 0.2 * l + 1.590 * m + 10} end,
  8591.     stalagmite          = function(l, m) return {0.2 * l + 0.810 * m + 04, 0.2 * l + 1.590 * m + 10} end,
  8592.     icicle              = function(l, m) return {0.2 * l + 1.810 * m + 10, 0.2 * l + 3.000 * m + 18} end,
  8593.     fireball            = function(l, m) return {0.2 * l + 1.810 * m + 10, 0.2 * l + 3.000 * m + 18} end,
  8594.     holy_missile        = function(l, m) return {0.2 * l + 1.790 * m + 11, 0.2 * l + 3.750 * m + 24} end,
  8595.     sudden_death        = function(l, m) return {0.2 * l + 4.605 * m + 28, 0.2 * l + 7.395 * m + 46} end,
  8596.     thunderstorm        = function(l, m) return {0.2 * l + 1.000 * m + 06, 0.2 * l + 2.600 * m + 16} end,
  8597.     stone_shower        = function(l, m) return {0.2 * l + 1.000 * m + 06, 0.2 * l + 2.600 * m + 16} end,
  8598.     avalanche           = function(l, m) return {0.2 * l + 1.200 * m + 07, 0.2 * l + 2.800 * m + 17} end,
  8599.     great_fireball      = function(l, m) return {0.2 * l + 1.200 * m + 07, 0.2 * l + 2.800 * m + 17} end,
  8600.     explosion           = function(l, m) return {0.2 * l + 0.0 * m, 0.2 * l + 4.8 * m} end,
  8601.     energy_beam         = function(l, m) return {0.2 * l + 2.5 * m, 0.2 * l + 4.0 * m} end,
  8602.     great_energy_beam   = function(l, m) return {0.2 * l + 4.0 * m, 0.2 * l + 7.0 * m} end,
  8603.     divine_caldera      = function(l, m) return {0.2 * l + 4.0 * m, 0.2 * l + 6.0 * m} end,
  8604.     terra_wave          = function(l, m) return {0.2 * l + 3.5 * m, 0.2 * l + 7.0 * m} end,
  8605.     energy_wave         = function(l, m) return {0.2 * l + 4.5 * m, 0.2 * l + 9.0 * m} end,
  8606.     heal_friend         = function(l, m) return {0.2 * l + 010 * m, 0.2 * l + 014 * m} end,
  8607.     rage_of_the_skies   = function(l, m) return {0.2 * l + 5.0 * m, 0.2 * l + 012 * m} end,
  8608.     hells_core          = function(l, m) return {0.2 * l + 7.0 * m, 0.2 * l + 014 * m} end,
  8609.     wrath_of_nature     = function(l, m) return {0.2 * l + 5.0 * m, 0.2 * l + 010 * m} end,
  8610.     eternal_winter      = function(l, m) return {0.2 * l + 6.0 * m, 0.2 * l + 012 * m} end,
  8611.     divine_healing      = function(l, m) return {0.2 * l + 18.5 * m, 0.2 * l + 025 * m} end,
  8612.     light_healing       = function(l, m) return {0.2 * l + 1.400 * m + 08, 0.2 * l + 1.795 * m + 11} end,
  8613.     intense_healing     = function(l, m) return {0.2 * l + 3.184 * m + 20, 0.2 * l + 5.590 * m + 35} end,
  8614.     ultimate_healing    = function(l, m) return {0.2 * l + 7.220 * m + 44, 0.2 * l + 12.79 * m + 79} end,
  8615.     wound_cleansing     = function(l, m) return {0.2 * l + 4.000 * m + 25, 0.2 * l + 7.750 * m + 50} end,
  8616.     mass_healing        = function(l, m) return {0.2 * l + 5.700 * m + 26, 0.2 * l + 10.43 * m + 62} end,
  8617. }
  8618.  
  8619. creatures_table = {
  8620.     {name = "achad", exp = 70, hp = 185, ratio = 0.378, maxdmg = 80, deathmod = 100, firemod = 90, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8621.     {name = "acid blob", exp = 250, hp = 250, ratio = 1.000, maxdmg = 160, deathmod = 0, firemod = 110, energymod = 110, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8622.     {name = "acolyte of darkness", exp = 200, hp = 325, ratio = 0.615, maxdmg = 120, deathmod = 0, firemod = 0, energymod = 80, earthmod = 0, icemod = 90, holymod = 105, physicalmod = 105},
  8623.     {name = "acolyte of the cult", exp = 300, hp = 390, ratio = 0.769, maxdmg = 220, deathmod = 105, firemod = 100, energymod = 110, earthmod = 80, icemod = 80, holymod = 80, physicalmod = 110},
  8624.     {name = "adept of the cult", exp = 400, hp = 430, ratio = 0.930, maxdmg = 242, deathmod = 105, firemod = 100, energymod = 105, earthmod = 60, icemod = 80, holymod = 70, physicalmod = 100},
  8625.     {name = "amazon", exp = 60, hp = 110, ratio = 0.545, maxdmg = 60, deathmod = 105, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 105},
  8626.     {name = "ancient scarab", exp = 720, hp = 1000, ratio = 0.720, maxdmg = 380, deathmod = 100, firemod = 120, energymod = 80, earthmod = 0, icemod = 105, holymod = 100, physicalmod = 90},
  8627.     {name = "anmothra", exp = 10000, hp = 2100, ratio = 4.762, maxdmg = 350, deathmod = 110, firemod = 0, energymod = 75, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  8628.     {name = "annihilon", exp = 15000, hp = 40000, ratio = 0.375, maxdmg = 2650, deathmod = 5, firemod = 100, energymod = 5, earthmod = 100, icemod = 80, holymod = 105, physicalmod = 100},
  8629.     {name = "apocalypse", exp = 80000, hp = 160000, ratio = 0.500, maxdmg = 9800, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8630.     {name = "apprentice sheng", exp = 150, hp = 95, ratio = 1.579, maxdmg = 80, deathmod = 100, firemod = 100, energymod = 0, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8631.     {name = "arachir the ancient one", exp = 1800, hp = 1600, ratio = 1.125, maxdmg = 480, deathmod = 0, firemod = 101, energymod = 80, earthmod = 100, icemod = 95, holymod = 105, physicalmod = 99},
  8632.     {name = "arkhothep", exp = 0, hp = 1, ratio = 0.000, maxdmg = 5000, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8633.     {name = "armenius", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8634.     {name = "arthei", exp = 4000, hp = 4200, ratio = 0.952, maxdmg = 1000, deathmod = 0, firemod = 101, energymod = 100, earthmod = 0, icemod = 100, holymod = 105, physicalmod = 100},
  8635.     {name = "ashmunrah", exp = 3100, hp = 5000, ratio = 0.620, maxdmg = 2412, deathmod = 0, firemod = 105, energymod = 80, earthmod = 75, icemod = 80, holymod = 110, physicalmod = 90},
  8636.     {name = "assassin", exp = 105, hp = 175, ratio = 0.600, maxdmg = 160, deathmod = 105, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 105},
  8637.     {name = "avalanche", exp = 305, hp = 550, ratio = 0.555, maxdmg = 250, deathmod = 100, firemod = 70, energymod = 110, earthmod = 0, icemod = 0, holymod = 100, physicalmod = 100},
  8638.     {name = "axeitus headbanger", exp = 140, hp = 365, ratio = 0.384, maxdmg = 130, deathmod = 100, firemod = 105, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8639.     {name = "azerus", exp = 6000, hp = 7500, ratio = 0.800, maxdmg = 1000, deathmod = 85, firemod = 85, energymod = 85, earthmod = 85, icemod = 85, holymod = 85, physicalmod = 100},
  8640.     {name = "azure frog", exp = 20, hp = 60, ratio = 0.333, maxdmg = 24, deathmod = 100, firemod = 110, energymod = 100, earthmod = 100, icemod = 90, holymod = 100, physicalmod = 100},
  8641.     {name = "badger", exp = 5, hp = 23, ratio = 0.217, maxdmg = 12, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8642.     {name = "bandit", exp = 65, hp = 245, ratio = 0.265, maxdmg = 43, deathmod = 105, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 110},
  8643.     {name = "bane of light", exp = 450, hp = 925, ratio = 0.486, maxdmg = 0, deathmod = 0, firemod = 0, energymod = 95, earthmod = 0, icemod = 0, holymod = 125, physicalmod = 65},
  8644.     {name = "banshee", exp = 900, hp = 1000, ratio = 0.900, maxdmg = 652, deathmod = 0, firemod = 0, energymod = 100, earthmod = 0, icemod = 100, holymod = 125, physicalmod = 100},
  8645.     {name = "barbaria", exp = 355, hp = 345, ratio = 1.029, maxdmg = 170, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8646.     {name = "barbarian bloodwalker", exp = 195, hp = 305, ratio = 0.639, maxdmg = 200, deathmod = 101, firemod = 100, energymod = 90, earthmod = 105, icemod = 50, holymod = 80, physicalmod = 95},
  8647.     {name = "barbarian brutetamer", exp = 90, hp = 145, ratio = 0.621, maxdmg = 54, deathmod = 101, firemod = 100, energymod = 80, earthmod = 100, icemod = 50, holymod = 90, physicalmod = 120},
  8648.     {name = "barbarian headsplitter", exp = 85, hp = 100, ratio = 0.850, maxdmg = 110, deathmod = 101, firemod = 100, energymod = 80, earthmod = 110, icemod = 50, holymod = 90, physicalmod = 100},
  8649.     {name = "barbarian skullhunter", exp = 85, hp = 135, ratio = 0.630, maxdmg = 65, deathmod = 101, firemod = 100, energymod = 80, earthmod = 110, icemod = 50, holymod = 90, physicalmod = 95},
  8650.     {name = "baron brute", exp = 3000, hp = 5025, ratio = 0.597, maxdmg = 474, deathmod = 100, firemod = 20, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8651.     {name = "bat", exp = 10, hp = 30, ratio = 0.333, maxdmg = 8, deathmod = 100, firemod = 100, energymod = 100, earthmod = 120, icemod = 100, holymod = 100, physicalmod = 100},
  8652.     {name = "battlemaster zunzu", exp = 2500, hp = 5000, ratio = 0.500, maxdmg = 650, deathmod = 90, firemod = 75, energymod = 80, earthmod = 0, icemod = 85, holymod = 100, physicalmod = 85},
  8653.     {name = "bazir", exp = 0, hp = 1, ratio = 0.000, maxdmg = 4000, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8654.     {name = "bear", exp = 23, hp = 80, ratio = 0.287, maxdmg = 25, deathmod = 105, firemod = 100, energymod = 100, earthmod = 100, icemod = 110, holymod = 90, physicalmod = 100},
  8655.     {name = "behemoth", exp = 2500, hp = 4000, ratio = 0.625, maxdmg = 635, deathmod = 105, firemod = 70, energymod = 90, earthmod = 20, icemod = 110, holymod = 70, physicalmod = 90},
  8656.     {name = "berserker chicken", exp = 220, hp = 465, ratio = 0.473, maxdmg = 270, deathmod = 90, firemod = 90, energymod = 90, earthmod = 90, icemod = 90, holymod = 90, physicalmod = 120},
  8657.     {name = "betrayed wraith", exp = 3500, hp = 4200, ratio = 0.833, maxdmg = 455, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 50, holymod = 120, physicalmod = 100},
  8658.     {name = "big boss trolliver", exp = 105, hp = 150, ratio = 0.700, maxdmg = 40, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8659.     {name = "black knight", exp = 1600, hp = 1800, ratio = 0.889, maxdmg = 500, deathmod = 80, firemod = 5, energymod = 20, earthmod = 0, icemod = 0, holymod = 108, physicalmod = 80},
  8660.     {name = "black sheep", exp = 0, hp = 20, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8661.     {name = "blazing fire elemental", exp = 450, hp = 650, ratio = 0.692, maxdmg = 450, deathmod = 70, firemod = 0, energymod = 80, earthmod = 100, icemod = 125, holymod = 100, physicalmod = 100},
  8662.     {name = "blightwalker", exp = 5850, hp = 8900, ratio = 0.657, maxdmg = 900, deathmod = 0, firemod = 50, energymod = 80, earthmod = 0, icemod = 50, holymod = 130, physicalmod = 110},
  8663.     {name = "blistering fire elemental", exp = 1300, hp = 1500, ratio = 0.867, maxdmg = 975, deathmod = 60, firemod = 0, energymod = 80, earthmod = 50, icemod = 115, holymod = 0, physicalmod = 75},
  8664.     {name = "blood crab", exp = 160, hp = 290, ratio = 0.552, maxdmg = 110, deathmod = 100, firemod = 110, energymod = 105, earthmod = 0, icemod = 0, holymod = 100, physicalmod = 80},
  8665.     {name = "blood crab", exp = 180, hp = 320, ratio = 0.562, maxdmg = 111, deathmod = 100, firemod = 0, energymod = 105, earthmod = 0, icemod = 0, holymod = 100, physicalmod = 99},
  8666.     {name = "bloodpaw", exp = 50, hp = 100, ratio = 0.500, maxdmg = 40, deathmod = 100, firemod = 80, energymod = 110, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8667.     {name = "bloom of doom", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8668.     {name = "blue djinn", exp = 215, hp = 330, ratio = 0.652, maxdmg = 325, deathmod = 112, firemod = 20, energymod = 50, earthmod = 100, icemod = 110, holymod = 99, physicalmod = 100},
  8669.     {name = "bog raider", exp = 800, hp = 1300, ratio = 0.615, maxdmg = 600, deathmod = 95, firemod = 15, energymod = 110, earthmod = 70, icemod = 105, holymod = 105, physicalmod = 120},
  8670.     {name = "bonebeast", exp = 580, hp = 515, ratio = 1.126, maxdmg = 340, deathmod = 0, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 120, physicalmod = 100},
  8671.     {name = "bonelord", exp = 170, hp = 260, ratio = 0.654, maxdmg = 235, deathmod = 100, firemod = 110, energymod = 100, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8672.     {name = "bones", exp = 3750, hp = 9500, ratio = 0.395, maxdmg = 1200, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8673.     {name = "boogey", exp = 475, hp = 930, ratio = 0.511, maxdmg = 200, deathmod = 0, firemod = 110, energymod = 110, earthmod = 60, icemod = 75, holymod = 110, physicalmod = 100},
  8674.     {name = "boreth", exp = 1800, hp = 1400, ratio = 1.286, maxdmg = 800, deathmod = 0, firemod = 101, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8675.     {name = "bovinus", exp = 60, hp = 150, ratio = 0.400, maxdmg = 50, deathmod = 100, firemod = 80, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8676.     {name = "braindeath", exp = 985, hp = 1225, ratio = 0.804, maxdmg = 700, deathmod = 0, firemod = 115, energymod = 90, earthmod = 0, icemod = 80, holymod = 120, physicalmod = 90},
  8677.     {name = "bride of night", exp = 450, hp = 275, ratio = 1.636, maxdmg = 100, deathmod = 80, firemod = 100, energymod = 100, earthmod = 100, icemod = 120, holymod = 100, physicalmod = 100},
  8678.     {name = "brimstone bug", exp = 900, hp = 1300, ratio = 0.692, maxdmg = 420, deathmod = 0, firemod = 110, energymod = 110, earthmod = 0, icemod = 110, holymod = 110, physicalmod = 105},
  8679.     {name = "brutus bloodbeard", exp = 795, hp = 1200, ratio = 0.662, maxdmg = 350, deathmod = 100, firemod = 100, energymod = 101, earthmod = 100, icemod = 101, holymod = 99, physicalmod = 100},
  8680.     {name = "bug", exp = 18, hp = 29, ratio = 0.621, maxdmg = 23, deathmod = 100, firemod = 110, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8681.     {name = "butterfly", exp = 0, hp = 2, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8682.     {name = "cake golem", exp = 0, hp = 1, ratio = 0.000, maxdmg = 120, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8683.     {name = "captain jones", exp = 825, hp = 800, ratio = 1.031, maxdmg = 400, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 0},
  8684.     {name = "carniphila", exp = 150, hp = 255, ratio = 0.588, maxdmg = 330, deathmod = 100, firemod = 120, energymod = 90, earthmod = 0, icemod = 65, holymod = 100, physicalmod = 100},
  8685.     {name = "carrion worm", exp = 70, hp = 145, ratio = 0.483, maxdmg = 45, deathmod = 100, firemod = 105, energymod = 99, earthmod = 80, icemod = 105, holymod = 100, physicalmod = 100},
  8686.     {name = "cat", exp = 0, hp = 20, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8687.     {name = "cave rat", exp = 10, hp = 30, ratio = 0.333, maxdmg = 10, deathmod = 100, firemod = 110, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8688.     {name = "centipede", exp = 34, hp = 70, ratio = 0.486, maxdmg = 46, deathmod = 100, firemod = 115, energymod = 90, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8689.     {name = "chakoya toolshaper", exp = 40, hp = 80, ratio = 0.500, maxdmg = 80, deathmod = 105, firemod = 60, energymod = 115, earthmod = 100, icemod = 0, holymod = 90, physicalmod = 100},
  8690.     {name = "chakoya tribewarden", exp = 40, hp = 68, ratio = 0.588, maxdmg = 30, deathmod = 105, firemod = 75, energymod = 115, earthmod = 100, icemod = 0, holymod = 90, physicalmod = 100},
  8691.     {name = "chakoya windcaller", exp = 48, hp = 84, ratio = 0.571, maxdmg = 82, deathmod = 110, firemod = 50, energymod = 115, earthmod = 100, icemod = 0, holymod = 80, physicalmod = 100},
  8692.     {name = "charged energy elemental", exp = 450, hp = 500, ratio = 0.900, maxdmg = 375, deathmod = 100, firemod = 0, energymod = 0, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 105},
  8693.     {name = "chicken", exp = 0, hp = 15, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8694.     {name = "chikhaton", exp = 35000, hp = 1, ratio = 35000.000, maxdmg = 1130, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8695.     {name = "chizzoron the distorter", exp = 0, hp = 8000, ratio = 0.000, maxdmg = 2300, deathmod = 70, firemod = 100, energymod = 80, earthmod = 0, icemod = 80, holymod = 90, physicalmod = 100},
  8696.     {name = "cobra", exp = 30, hp = 65, ratio = 0.462, maxdmg = 5, deathmod = 100, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8697.     {name = "cockroach", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8698.     {name = "cocoon", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8699.     {name = "coldheart", exp = 3500, hp = 7000, ratio = 0.500, maxdmg = 675, deathmod = 100, firemod = 0, energymod = 100, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 100},
  8700.     {name = "colerian the barbarian", exp = 90, hp = 265, ratio = 0.340, maxdmg = 100, deathmod = 100, firemod = 100, energymod = 80, earthmod = 120, icemod = 100, holymod = 100, physicalmod = 100},
  8701.     {name = "coral frog", exp = 20, hp = 60, ratio = 0.333, maxdmg = 24, deathmod = 100, firemod = 110, energymod = 100, earthmod = 100, icemod = 90, holymod = 100, physicalmod = 100},
  8702.     {name = "countess sorrow", exp = 13000, hp = 6500, ratio = 2.000, maxdmg = 2905, deathmod = 0, firemod = 110, energymod = 90, earthmod = 0, icemod = 50, holymod = 100, physicalmod = 0},
  8703.     {name = "crab", exp = 30, hp = 55, ratio = 0.545, maxdmg = 20, deathmod = 100, firemod = 110, energymod = 110, earthmod = 0, icemod = 99, holymod = 100, physicalmod = 100},
  8704.     {name = "crazed beggar", exp = 35, hp = 100, ratio = 0.350, maxdmg = 25, deathmod = 110, firemod = 100, energymod = 80, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 95},
  8705.     {name = "crimson frog", exp = 20, hp = 60, ratio = 0.333, maxdmg = 24, deathmod = 100, firemod = 110, energymod = 100, earthmod = 100, icemod = 90, holymod = 100, physicalmod = 100},
  8706.     {name = "crocodile", exp = 40, hp = 105, ratio = 0.381, maxdmg = 40, deathmod = 100, firemod = 110, energymod = 105, earthmod = 80, icemod = 90, holymod = 100, physicalmod = 105},
  8707.     {name = "crypt shambler", exp = 195, hp = 330, ratio = 0.591, maxdmg = 195, deathmod = 0, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 125, physicalmod = 100},
  8708.     {name = "crystal spider", exp = 900, hp = 1250, ratio = 0.720, maxdmg = 358, deathmod = 100, firemod = 0, energymod = 120, earthmod = 80, icemod = 0, holymod = 100, physicalmod = 100},
  8709.     {name = "cublarc the plunderer", exp = 400, hp = 400, ratio = 1.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8710.     {name = "cursed gladiator", exp = 215, hp = 435, ratio = 0.494, maxdmg = 200, deathmod = 100, firemod = 105, energymod = 100, earthmod = 80, icemod = 100, holymod = 100, physicalmod = 100},
  8711.     {name = "cyclops", exp = 150, hp = 260, ratio = 0.577, maxdmg = 105, deathmod = 110, firemod = 100, energymod = 75, earthmod = 110, icemod = 100, holymod = 80, physicalmod = 100},
  8712.     {name = "cyclops drone", exp = 200, hp = 325, ratio = 0.615, maxdmg = 180, deathmod = 105, firemod = 100, energymod = 90, earthmod = 110, icemod = 80, holymod = 99, physicalmod = 100},
  8713.     {name = "cyclops smith", exp = 255, hp = 435, ratio = 0.586, maxdmg = 220, deathmod = 105, firemod = 90, energymod = 80, earthmod = 110, icemod = 100, holymod = 99, physicalmod = 100},
  8714.     {name = "damaged worker golem", exp = 95, hp = 260, ratio = 0.365, maxdmg = 90, deathmod = 90, firemod = 100, energymod = 105, earthmod = 50, icemod = 90, holymod = 50, physicalmod = 75},
  8715.     {name = "darakan the executioner", exp = 1600, hp = 3500, ratio = 0.457, maxdmg = 390, deathmod = 100, firemod = 101, energymod = 100, earthmod = 100, icemod = 99, holymod = 100, physicalmod = 100},
  8716.     {name = "dark apprentice", exp = 100, hp = 225, ratio = 0.444, maxdmg = 100, deathmod = 105, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8717.     {name = "dark magician", exp = 185, hp = 325, ratio = 0.569, maxdmg = 100, deathmod = 101, firemod = 90, energymod = 80, earthmod = 80, icemod = 90, holymod = 80, physicalmod = 100},
  8718.     {name = "dark monk", exp = 145, hp = 190, ratio = 0.763, maxdmg = 150, deathmod = 60, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 110, physicalmod = 120},
  8719.     {name = "dark torturer", exp = 4650, hp = 7350, ratio = 0.633, maxdmg = 1300, deathmod = 90, firemod = 0, energymod = 70, earthmod = 10, icemod = 110, holymod = 110, physicalmod = 100},
  8720.     {name = "deadeye devious", exp = 500, hp = 1450, ratio = 0.345, maxdmg = 250, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8721.     {name = "death blob", exp = 300, hp = 320, ratio = 0.938, maxdmg = 212, deathmod = 0, firemod = 110, energymod = 110, earthmod = 0, icemod = 90, holymod = 110, physicalmod = 70},
  8722.     {name = "deathbringer", exp = 5100, hp = 10000, ratio = 0.510, maxdmg = 1265, deathmod = 0, firemod = 0, energymod = 120, earthmod = 0, icemod = 0, holymod = 110, physicalmod = 100},
  8723.     {name = "deathslicer", exp = 0, hp = 1, ratio = 0.000, maxdmg = 1000, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8724.     {name = "deathspawn", exp = 0, hp = 225, ratio = 0.000, maxdmg = 1000, deathmod = 0, firemod = 85, energymod = 85, earthmod = 0, icemod = 85, holymod = 110, physicalmod = 100},
  8725.     {name = "deer", exp = 0, hp = 25, ratio = 0.000, maxdmg = 1, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8726.     {name = "defiler", exp = 3700, hp = 3650, ratio = 1.014, maxdmg = 712, deathmod = 100, firemod = 125, energymod = 90, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8727.     {name = "demodras", exp = 6000, hp = 4500, ratio = 1.333, maxdmg = 1150, deathmod = 100, firemod = 0, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8728.     {name = "demon", exp = 6000, hp = 8200, ratio = 0.732, maxdmg = 1530, deathmod = 70, firemod = 0, energymod = 50, earthmod = 60, icemod = 112, holymod = 112, physicalmod = 70},
  8729.     {name = "demon parrot", exp = 225, hp = 360, ratio = 0.625, maxdmg = 190, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8730.     {name = "demon skeleton", exp = 240, hp = 400, ratio = 0.600, maxdmg = 235, deathmod = 0, firemod = 0, energymod = 100, earthmod = 0, icemod = 100, holymod = 125, physicalmod = 100},
  8731.     {name = "demon (goblin)", exp = 25, hp = 50, ratio = 0.500, maxdmg = 30, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8732.     {name = "destroyer", exp = 2500, hp = 3700, ratio = 0.676, maxdmg = 700, deathmod = 80, firemod = 70, energymod = 0, earthmod = 80, icemod = 115, holymod = 103, physicalmod = 99},
  8733.     {name = "devovorga", exp = 0, hp = 1, ratio = 0.000, maxdmg = 9400, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8734.     {name = "dharalion", exp = 380, hp = 380, ratio = 1.000, maxdmg = 120, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8735.     {name = "diabolic imp", exp = 2900, hp = 1950, ratio = 1.487, maxdmg = 870, deathmod = 90, firemod = 0, energymod = 100, earthmod = 50, icemod = 110, holymod = 110, physicalmod = 100},
  8736.     {name = "diblis the fair", exp = 1800, hp = 1500, ratio = 1.200, maxdmg = 1500, deathmod = 0, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 105, physicalmod = 60},
  8737.     {name = "dipthrah", exp = 2900, hp = 4200, ratio = 0.690, maxdmg = 1400, deathmod = 0, firemod = 100, energymod = 80, earthmod = 80, icemod = 100, holymod = 110, physicalmod = 0},
  8738.     {name = "dire penguin", exp = 119, hp = 173, ratio = 0.688, maxdmg = 115, deathmod = 100, firemod = 50, energymod = 105, earthmod = 50, icemod = 100, holymod = 100, physicalmod = 100},
  8739.     {name = "dirtbeard", exp = 375, hp = 630, ratio = 0.595, maxdmg = 225, deathmod = 100, firemod = 110, energymod = 100, earthmod = 80, icemod = 105, holymod = 90, physicalmod = 100},
  8740.     {name = "diseased bill", exp = 300, hp = 2000, ratio = 0.150, maxdmg = 769, deathmod = 25, firemod = 75, energymod = 75, earthmod = 0, icemod = 75, holymod = 75, physicalmod = 90},
  8741.     {name = "diseased dan", exp = 300, hp = 2000, ratio = 0.150, maxdmg = 381, deathmod = 95, firemod = 15, energymod = 110, earthmod = 80, icemod = 105, holymod = 105, physicalmod = 105},
  8742.     {name = "diseased fred", exp = 300, hp = 2000, ratio = 0.150, maxdmg = 450, deathmod = 45, firemod = 85, energymod = 85, earthmod = 0, icemod = 85, holymod = 85, physicalmod = 85},
  8743.     {name = "doctor perhaps", exp = 325, hp = 475, ratio = 0.684, maxdmg = 100, deathmod = 100, firemod = 90, energymod = 80, earthmod = 80, icemod = 80, holymod = 80, physicalmod = 105},
  8744.     {name = "dog", exp = 0, hp = 20, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8745.     {name = "doom deer", exp = 200, hp = 405, ratio = 0.494, maxdmg = 155, deathmod = 100, firemod = 100, energymod = 0, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8746.     {name = "doomhowl", exp = 3750, hp = 8500, ratio = 0.441, maxdmg = 644, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 85},
  8747.     {name = "doomsday cultist", exp = 100, hp = 125, ratio = 0.800, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8748.     {name = "dracola", exp = 11000, hp = 16200, ratio = 0.679, maxdmg = 4245, deathmod = 0, firemod = 0, energymod = 100, earthmod = 0, icemod = 0, holymod = 110, physicalmod = 100},
  8749.     {name = "dragon", exp = 700, hp = 1000, ratio = 0.700, maxdmg = 400, deathmod = 100, firemod = 0, energymod = 80, earthmod = 20, icemod = 110, holymod = 100, physicalmod = 100},
  8750.     {name = "dragon hatchling", exp = 185, hp = 380, ratio = 0.487, maxdmg = 200, deathmod = 100, firemod = 0, energymod = 105, earthmod = 25, icemod = 110, holymod = 100, physicalmod = 100},
  8751.     {name = "dragon lord", exp = 2100, hp = 1900, ratio = 1.105, maxdmg = 720, deathmod = 100, firemod = 0, energymod = 80, earthmod = 20, icemod = 110, holymod = 100, physicalmod = 100},
  8752.     {name = "dragon lord hatchling", exp = 645, hp = 750, ratio = 0.860, maxdmg = 335, deathmod = 100, firemod = 0, energymod = 110, earthmod = 90, icemod = 110, holymod = 100, physicalmod = 100},
  8753.     {name = "draken abomination", exp = 3800, hp = 6250, ratio = 0.608, maxdmg = 1000, deathmod = 0, firemod = 0, energymod = 105, earthmod = 0, icemod = 95, holymod = 105, physicalmod = 80},
  8754.     {name = "draken elite", exp = 4200, hp = 5550, ratio = 0.757, maxdmg = 1500, deathmod = 70, firemod = 0, energymod = 60, earthmod = 0, icemod = 100, holymod = 70, physicalmod = 85},
  8755.     {name = "draken spellweaver", exp = 2600, hp = 5000, ratio = 0.520, maxdmg = 1000, deathmod = 10, firemod = 0, energymod = 110, earthmod = 0, icemod = 110, holymod = 105, physicalmod = 110},
  8756.     {name = "draken warmaster", exp = 2400, hp = 4150, ratio = 0.578, maxdmg = 600, deathmod = 50, firemod = 0, energymod = 95, earthmod = 0, icemod = 105, holymod = 95, physicalmod = 95},
  8757.     {name = "drasilla", exp = 700, hp = 1320, ratio = 0.530, maxdmg = 390, deathmod = 100, firemod = 0, energymod = 80, earthmod = 100, icemod = 101, holymod = 100, physicalmod = 100},
  8758.     {name = "dreadbeast", exp = 250, hp = 800, ratio = 0.312, maxdmg = 140, deathmod = 0, firemod = 45, energymod = 85, earthmod = 0, icemod = 60, holymod = 150, physicalmod = 70},
  8759.     {name = "dreadmaw", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8760.     {name = "dreadwing", exp = 3750, hp = 8500, ratio = 0.441, maxdmg = 100, deathmod = 0, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8761.     {name = "dryad", exp = 190, hp = 310, ratio = 0.613, maxdmg = 120, deathmod = 100, firemod = 120, energymod = 70, earthmod = 0, icemod = 99, holymod = 100, physicalmod = 110},
  8762.     {name = "duskbringer", exp = 2600, hp = 3000, ratio = 0.867, maxdmg = 700, deathmod = 10, firemod = 110, energymod = 110, earthmod = 50, icemod = 115, holymod = 105, physicalmod = 99},
  8763.     {name = "dwarf", exp = 45, hp = 90, ratio = 0.500, maxdmg = 30, deathmod = 105, firemod = 105, energymod = 100, earthmod = 90, icemod = 100, holymod = 100, physicalmod = 100},
  8764.     {name = "dwarf dispenser", exp = 0, hp = 1, ratio = 0.000, maxdmg = 100, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8765.     {name = "dwarf geomancer", exp = 265, hp = 380, ratio = 0.697, maxdmg = 210, deathmod = 101, firemod = 40, energymod = 90, earthmod = 80, icemod = 105, holymod = 90, physicalmod = 100},
  8766.     {name = "dwarf guard", exp = 165, hp = 245, ratio = 0.673, maxdmg = 140, deathmod = 105, firemod = 105, energymod = 100, earthmod = 80, icemod = 100, holymod = 100, physicalmod = 90},
  8767.     {name = "dwarf henchman", exp = 15, hp = 350, ratio = 0.043, maxdmg = 93, deathmod = 85, firemod = 110, energymod = 100, earthmod = 100, icemod = 85, holymod = 100, physicalmod = 80},
  8768.     {name = "dwarf miner", exp = 60, hp = 120, ratio = 0.500, maxdmg = 30, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8769.     {name = "dwarf soldier", exp = 70, hp = 135, ratio = 0.519, maxdmg = 130, deathmod = 105, firemod = 105, energymod = 100, earthmod = 90, icemod = 100, holymod = 100, physicalmod = 100},
  8770.     {name = "dworc fleshhunter", exp = 40, hp = 85, ratio = 0.471, maxdmg = 41, deathmod = 115, firemod = 110, energymod = 100, earthmod = 0, icemod = 110, holymod = 100, physicalmod = 100},
  8771.     {name = "dworc venomsniper", exp = 35, hp = 80, ratio = 0.438, maxdmg = 17, deathmod = 110, firemod = 115, energymod = 100, earthmod = 0, icemod = 113, holymod = 80, physicalmod = 100},
  8772.     {name = "dworc voodoomaster", exp = 55, hp = 80, ratio = 0.688, maxdmg = 90, deathmod = 110, firemod = 115, energymod = 100, earthmod = 0, icemod = 110, holymod = 70, physicalmod = 100},
  8773.     {name = "earth elemental", exp = 450, hp = 650, ratio = 0.692, maxdmg = 328, deathmod = 50, firemod = 125, energymod = 0, earthmod = 0, icemod = 15, holymod = 50, physicalmod = 50},
  8774.     {name = "earth overlord", exp = 2800, hp = 4000, ratio = 0.700, maxdmg = 1500, deathmod = 80, firemod = 125, energymod = 100, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8775.     {name = "eclipse knight", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8776.     {name = "efreet", exp = 410, hp = 550, ratio = 0.745, maxdmg = 340, deathmod = 99, firemod = 10, energymod = 40, earthmod = 90, icemod = 105, holymod = 108, physicalmod = 100},
  8777.     {name = "elder bonelord", exp = 280, hp = 500, ratio = 0.560, maxdmg = 405, deathmod = 70, firemod = 110, energymod = 80, earthmod = 0, icemod = 70, holymod = 100, physicalmod = 100},
  8778.     {name = "elephant", exp = 160, hp = 320, ratio = 0.500, maxdmg = 100, deathmod = 100, firemod = 100, energymod = 110, earthmod = 100, icemod = 80, holymod = 100, physicalmod = 75},
  8779.     {name = "elf", exp = 42, hp = 100, ratio = 0.420, maxdmg = 40, deathmod = 101, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 80, physicalmod = 100},
  8780.     {name = "elf arcanist", exp = 175, hp = 220, ratio = 0.795, maxdmg = 220, deathmod = 80, firemod = 50, energymod = 80, earthmod = 100, icemod = 100, holymod = 110, physicalmod = 100},
  8781.     {name = "elf scout", exp = 75, hp = 160, ratio = 0.469, maxdmg = 110, deathmod = 101, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 80, physicalmod = 100},
  8782.     {name = "energy elemental", exp = 550, hp = 500, ratio = 1.100, maxdmg = 582, deathmod = 95, firemod = 0, energymod = 0, earthmod = 115, icemod = 0, holymod = 90, physicalmod = 70},
  8783.     {name = "energy overlord", exp = 2800, hp = 4000, ratio = 0.700, maxdmg = 1400, deathmod = 100, firemod = 101, energymod = 0, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 50},
  8784.     {name = "enlightened of the cult", exp = 500, hp = 700, ratio = 0.714, maxdmg = 285, deathmod = 101, firemod = 100, energymod = 101, earthmod = 100, icemod = 99, holymod = 80, physicalmod = 90},
  8785.     {name = "enraged bookworm", exp = 55, hp = 145, ratio = 0.379, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8786.     {name = "enraged squirrel", exp = 0, hp = 35, ratio = 0.000, maxdmg = 6, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8787.     {name = "esmeralda", exp = 600, hp = 800, ratio = 0.750, maxdmg = 384, deathmod = 0, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8788.     {name = "essence of darkness", exp = 30, hp = 1000, ratio = 0.030, maxdmg = 25, deathmod = 0, firemod = 2, energymod = 0, earthmod = 0, icemod = 0, holymod = 20, physicalmod = 0},
  8789.     {name = "eternal guardian", exp = 1800, hp = 2500, ratio = 0.720, maxdmg = 300, deathmod = 80, firemod = 30, energymod = 90, earthmod = 0, icemod = 90, holymod = 80, physicalmod = 100},
  8790.     {name = "evil mastermind", exp = 675, hp = 1295, ratio = 0.521, maxdmg = 357, deathmod = 0, firemod = 100, energymod = 10, earthmod = 0, icemod = 80, holymod = 105, physicalmod = 95},
  8791.     {name = "evil sheep", exp = 240, hp = 350, ratio = 0.686, maxdmg = 140, deathmod = 100, firemod = 110, energymod = 100, earthmod = 100, icemod = 80, holymod = 100, physicalmod = 80},
  8792.     {name = "evil sheep lord", exp = 340, hp = 400, ratio = 0.850, maxdmg = 118, deathmod = 100, firemod = 105, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 120},
  8793.     {name = "eye of the seven", exp = 0, hp = 1, ratio = 0.000, maxdmg = 500, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8794.     {name = "fahim the wise", exp = 1500, hp = 2000, ratio = 0.750, maxdmg = 800, deathmod = 110, firemod = 99, energymod = 100, earthmod = 100, icemod = 115, holymod = 99, physicalmod = 100},
  8795.     {name = "fallen mooh'tah master ghar", exp = 4400, hp = 8000, ratio = 0.550, maxdmg = 1600, deathmod = 100, firemod = 40, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8796.     {name = "fatality", exp = 4285, hp = 5945, ratio = 0.721, maxdmg = 205, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8797.     {name = "fernfang", exp = 600, hp = 400, ratio = 1.500, maxdmg = 230, deathmod = 100, firemod = 100, energymod = 100, earthmod = 50, icemod = 30, holymod = 100, physicalmod = 100},
  8798.     {name = "ferumbras", exp = 12000, hp = 35000, ratio = 0.343, maxdmg = 2400, deathmod = 100, firemod = 10, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8799.     {name = "fire devil", exp = 145, hp = 200, ratio = 0.725, maxdmg = 160, deathmod = 95, firemod = 0, energymod = 70, earthmod = 80, icemod = 120, holymod = 110, physicalmod = 105},
  8800.     {name = "fire elemental", exp = 220, hp = 280, ratio = 0.786, maxdmg = 280, deathmod = 0, firemod = 0, energymod = 100, earthmod = 100, icemod = 125, holymod = 100, physicalmod = 100},
  8801.     {name = "fire overlord", exp = 2800, hp = 4000, ratio = 0.700, maxdmg = 1200, deathmod = 80, firemod = 0, energymod = 80, earthmod = 20, icemod = 125, holymod = 100, physicalmod = 99},
  8802.     {name = "flamecaller zazrak", exp = 2000, hp = 3000, ratio = 0.667, maxdmg = 560, deathmod = 100, firemod = 100, energymod = 100, earthmod = 0, icemod = 110, holymod = 100, physicalmod = 100},
  8803.     {name = "flamethrower", exp = 0, hp = 1, ratio = 0.000, maxdmg = 100, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8804.     {name = "flamingo", exp = 0, hp = 25, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8805.     {name = "fleabringer", exp = 0, hp = 265, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8806.     {name = "fluffy", exp = 3550, hp = 4500, ratio = 0.789, maxdmg = 750, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8807.     {name = "foreman kneebiter", exp = 445, hp = 570, ratio = 0.781, maxdmg = 317, deathmod = 101, firemod = 101, energymod = 100, earthmod = 99, icemod = 100, holymod = 100, physicalmod = 99},
  8808.     {name = "freegoiz", exp = 0, hp = 1, ratio = 0.000, maxdmg = 1665, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8809.     {name = "frost dragon", exp = 2100, hp = 1800, ratio = 1.167, maxdmg = 700, deathmod = 90, firemod = 0, energymod = 100, earthmod = 0, icemod = 0, holymod = 100, physicalmod = 90},
  8810.     {name = "frost dragon hatchling", exp = 745, jp = 800, ratio = 0.931, maxdmg = 380, deathmod = 100, firemod = 0, energymod = 105, earthmod = 0, icemod = 0, holymod = 100, physicalmod = 100},
  8811.     {name = "frost giant", exp = 150, hp = 270, ratio = 0.556, maxdmg = 200, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 100},
  8812.     {name = "frost giantess", exp = 150, hp = 275, ratio = 0.545, maxdmg = 150, deathmod = 103, firemod = 80, energymod = 110, earthmod = 100, icemod = 0, holymod = 90, physicalmod = 100},
  8813.     {name = "frost troll", exp = 23, hp = 55, ratio = 0.418, maxdmg = 20, deathmod = 115, firemod = 50, energymod = 110, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  8814.     {name = "frostfur", exp = 35, hp = 65, ratio = 0.538, maxdmg = 30, deathmod = 100, firemod = 80, energymod = 110, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8815.     {name = "furious troll", exp = 185, hp = 245, ratio = 0.755, maxdmg = 100, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8816.     {name = "fury", exp = 4500, hp = 4100, ratio = 1.098, maxdmg = 800, deathmod = 110, firemod = 0, energymod = 110, earthmod = 110, icemod = 70, holymod = 70, physicalmod = 110},
  8817.     {name = "fury of the emperor", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 90, energymod = 110, earthmod = 0, icemod = 50, holymod = 115, physicalmod = 110},
  8818.     {name = "gamemaster", exp = 0, hp = 1, ratio = 0.000, maxdmg = 100, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8819.     {name = "gang member", exp = 70, hp = 295, ratio = 0.237, maxdmg = 95, deathmod = 105, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8820.     {name = "gargoyle", exp = 150, hp = 250, ratio = 0.600, maxdmg = 65, deathmod = 99, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 60},
  8821.     {name = "gazer", exp = 90, hp = 120, ratio = 0.750, maxdmg = 50, deathmod = 100, firemod = 110, energymod = 89, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8822.     {name = "general murius", exp = 450, hp = 550, ratio = 0.818, maxdmg = 250, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8823.     {name = "ghastly dragon", exp = 4600, hp = 7800, ratio = 0.590, maxdmg = 1780, deathmod = 0, firemod = 90, energymod = 110, earthmod = 0, icemod = 50, holymod = 115, physicalmod = 110},
  8824.     {name = "ghazbaran", exp = 15000, hp = 60000, ratio = 0.250, maxdmg = 5775, deathmod = 99, firemod = 0, energymod = 100, earthmod = 0, icemod = 0, holymod = 101, physicalmod = 99},
  8825.     {name = "ghost", exp = 120, hp = 150, ratio = 0.800, maxdmg = 125, deathmod = 0, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 0},
  8826.     {name = "ghost rat", exp = 0, hp = 1, ratio = 0.000, maxdmg = 120, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8827.     {name = "ghostly apparition", exp = 0, hp = 1, ratio = 0.000, maxdmg = 6, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8828.     {name = "ghoul", exp = 85, hp = 100, ratio = 0.850, maxdmg = 97, deathmod = 0, firemod = 100, energymod = 70, earthmod = 80, icemod = 90, holymod = 125, physicalmod = 100},
  8829.     {name = "giant spider", exp = 900, hp = 1300, ratio = 0.692, maxdmg = 378, deathmod = 100, firemod = 110, energymod = 80, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8830.     {name = "gladiator", exp = 90, hp = 185, ratio = 0.486, maxdmg = 90, deathmod = 101, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 90, physicalmod = 85},
  8831.     {name = "glitterscale", exp = 700, hp = 1000, ratio = 0.700, maxdmg = 0, deathmod = 100, firemod = 0, energymod = 100, earthmod = 20, icemod = 100, holymod = 100, physicalmod = 100},
  8832.     {name = "gloombringer", exp = 0, hp = 1, ratio = 0.000, maxdmg = 3000, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8833.     {name = "gnarlhound", exp = 60, hp = 198, ratio = 0.303, maxdmg = 70, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8834.     {name = "gnorre chyllson", exp = 4000, hp = 7100, ratio = 0.563, maxdmg = 1100, deathmod = 100, firemod = 0, energymod = 110, earthmod = 0, icemod = 0, holymod = 99, physicalmod = 101},
  8835.     {name = "goblin", exp = 25, hp = 50, ratio = 0.500, maxdmg = 35, deathmod = 110, firemod = 100, energymod = 80, earthmod = 112, icemod = 100, holymod = 99, physicalmod = 100},
  8836.     {name = "goblin assassin", exp = 52, hp = 75, ratio = 0.693, maxdmg = 50, deathmod = 101, firemod = 100, energymod = 80, earthmod = 110, icemod = 100, holymod = 99, physicalmod = 100},
  8837.     {name = "goblin leader", exp = 75, hp = 50, ratio = 1.500, maxdmg = 95, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8838.     {name = "goblin scavenger", exp = 37, hp = 60, ratio = 0.617, maxdmg = 75, deathmod = 110, firemod = 100, energymod = 80, earthmod = 110, icemod = 100, holymod = 99, physicalmod = 100},
  8839.     {name = "golgordan", exp = 10000, hp = 40000, ratio = 0.250, maxdmg = 3127, deathmod = 0, firemod = 101, energymod = 100, earthmod = 100, icemod = 101, holymod = 99, physicalmod = 99},
  8840.     {name = "gozzler", exp = 180, hp = 240, ratio = 0.750, maxdmg = 245, deathmod = 50, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 50, physicalmod = 105},
  8841.     {name = "grand mother foulscale", exp = 1400, hp = 1850, ratio = 0.757, maxdmg = 300, deathmod = 100, firemod = 0, energymod = 100, earthmod = 100, icemod = 105, holymod = 100, physicalmod = 100},
  8842.     {name = "grandfather tridian", exp = 1400, hp = 1800, ratio = 0.778, maxdmg = 540, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 65},
  8843.     {name = "gravelord oshuran", exp = 2400, hp = 3100, ratio = 0.774, maxdmg = 750, deathmod = 0, firemod = 100, energymod = 20, earthmod = 0, icemod = 50, holymod = 101, physicalmod = 100},
  8844.     {name = "green djinn", exp = 215, hp = 330, ratio = 0.652, maxdmg = 320, deathmod = 80, firemod = 20, energymod = 50, earthmod = 100, icemod = 110, holymod = 113, physicalmod = 80},
  8845.     {name = "green frog", exp = 0, hp = 25, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8846.     {name = "grim reaper", exp = 5500, hp = 3900, ratio = 1.410, maxdmg = 1720, deathmod = 20, firemod = 110, energymod = 110, earthmod = 60, icemod = 35, holymod = 110, physicalmod = 80},
  8847.     {name = "grimgor guteater", exp = 670, hp = 1155, ratio = 0.580, maxdmg = 330, deathmod = 101, firemod = 0, energymod = 80, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8848.     {name = "grorlam", exp = 2400, hp = 3000, ratio = 0.800, maxdmg = 530, deathmod = 101, firemod = 110, energymod = 80, earthmod = 0, icemod = 100, holymod = 80, physicalmod = 70},
  8849.     {name = "grynch clan goblin", exp = 4, hp = 80, ratio = 0.050, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8850.     {name = "hacker", exp = 45, hp = 430, ratio = 0.105, maxdmg = 35, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8851.     {name = "hairman the huge", exp = 335, hp = 600, ratio = 0.558, maxdmg = 110, deathmod = 101, firemod = 99, energymod = 99, earthmod = 99, icemod = 101, holymod = 100, physicalmod = 99},
  8852.     {name = "hand of cursed fate", exp = 5000, hp = 7500, ratio = 0.667, maxdmg = 920, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 110, holymod = 125, physicalmod = 100},
  8853.     {name = "harbinger of darkness", exp = 0, hp = 1, ratio = 0.000, maxdmg = 4066, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8854.     {name = "hatebreeder", exp = 11000, hp = 1, ratio = 11000.000, maxdmg = 1800, deathmod = 0, firemod = 90, energymod = 110, earthmod = 0, icemod = 50, holymod = 115, physicalmod = 110},
  8855.     {name = "haunted treeling", exp = 310, hp = 450, ratio = 0.689, maxdmg = 320, deathmod = 99, firemod = 105, energymod = 100, earthmod = 0, icemod = 85, holymod = 80, physicalmod = 100},
  8856.     {name = "haunter", exp = 4000, hp = 8500, ratio = 0.471, maxdmg = 210, deathmod = 90, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8857.     {name = "hell hole", exp = 0, hp = 1, ratio = 0.000, maxdmg = 1000, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8858.     {name = "hellfire fighter", exp = 3900, hp = 3800, ratio = 1.026, maxdmg = 2749, deathmod = 80, firemod = 0, energymod = 75, earthmod = 100, icemod = 125, holymod = 100, physicalmod = 50},
  8859.     {name = "hellgorak", exp = 10000, hp = 30000, ratio = 0.333, maxdmg = 1800, deathmod = 2, firemod = 2, energymod = 2, earthmod = 2, icemod = 2, holymod = 2, physicalmod = 2},
  8860.     {name = "hellhound", exp = 6800, hp = 7500, ratio = 0.907, maxdmg = 3342, deathmod = 100, firemod = 0, energymod = 90, earthmod = 80, icemod = 105, holymod = 125, physicalmod = 100},
  8861.     {name = "hellspawn", exp = 2550, hp = 3500, ratio = 0.729, maxdmg = 515, deathmod = 105, firemod = 60, energymod = 90, earthmod = 20, icemod = 110, holymod = 70, physicalmod = 80},
  8862.     {name = "heoni", exp = 515, hp = 900, ratio = 0.572, maxdmg = 100, deathmod = 100, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8863.     {name = "herald of gloom", exp = 450, hp = 450, ratio = 1.000, maxdmg = 0, deathmod = 105, firemod = 100, energymod = 105, earthmod = 100, icemod = 80, holymod = 80, physicalmod = 105},
  8864.     {name = "hero", exp = 1200, hp = 1400, ratio = 0.857, maxdmg = 360, deathmod = 120, firemod = 70, energymod = 60, earthmod = 50, icemod = 90, holymod = 50, physicalmod = 70},
  8865.     {name = "hide", exp = 240, hp = 500, ratio = 0.480, maxdmg = 144, deathmod = 100, firemod = 115, energymod = 90, earthmod = 0, icemod = 115, holymod = 100, physicalmod = 60},
  8866.     {name = "high templar cobrass", exp = 515, hp = 410, ratio = 1.256, maxdmg = 80, deathmod = 100, firemod = 110, energymod = 80, earthmod = 0, icemod = 99, holymod = 100, physicalmod = 100},
  8867.     {name = "hot dog", exp = 190, hp = 505, ratio = 0.376, maxdmg = 125, deathmod = 100, firemod = 0, energymod = 100, earthmod = 100, icemod = 100, holymod = 105, physicalmod = 120},
  8868.     {name = "hunter", exp = 150, hp = 150, ratio = 1.000, maxdmg = 120, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 80, physicalmod = 110},
  8869.     {name = "husky", exp = 0, hp = 140, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8870.     {name = "hyaena", exp = 20, hp = 60, ratio = 0.333, maxdmg = 20, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8871.     {name = "hydra", exp = 2100, hp = 2350, ratio = 0.894, maxdmg = 750, deathmod = 100, firemod = 100, energymod = 110, earthmod = 0, icemod = 50, holymod = 70, physicalmod = 105},
  8872.     {name = "ice golem", exp = 295, hp = 385, ratio = 0.766, maxdmg = 305, deathmod = 0, firemod = 0, energymod = 120, earthmod = 100, icemod = 0, holymod = 0, physicalmod = 75},
  8873.     {name = "ice overlord", exp = 2800, hp = 4000, ratio = 0.700, maxdmg = 1408, deathmod = 100, firemod = 0, energymod = 125, earthmod = 0, icemod = 0, holymod = 100, physicalmod = 50},
  8874.     {name = "ice witch", exp = 580, hp = 650, ratio = 0.892, maxdmg = 394, deathmod = 110, firemod = 50, energymod = 110, earthmod = 60, icemod = 0, holymod = 70, physicalmod = 100},
  8875.     {name = "incineron", exp = 3500, hp = 7000, ratio = 0.500, maxdmg = 1400, deathmod = 100, firemod = 0, energymod = 80, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 100},
  8876.     {name = "infernal frog", exp = 190, hp = 655, ratio = 0.290, maxdmg = 42, deathmod = 100, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8877.     {name = "infernalist", exp = 4000, hp = 3650, ratio = 1.096, maxdmg = 120, deathmod = 99, firemod = 0, energymod = 0, earthmod = 5, icemod = 105, holymod = 80, physicalmod = 101},
  8878.     {name = "infernatil", exp = 85000, hp = 160000, ratio = 0.531, maxdmg = 6000, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8879.     {name = "inky", exp = 250, hp = 600, ratio = 0.417, maxdmg = 367, deathmod = 100, firemod = 0, energymod = 105, earthmod = 10, icemod = 0, holymod = 100, physicalmod = 100},
  8880.     {name = "insect swarm", exp = 40, hp = 50, ratio = 0.800, maxdmg = 25, deathmod = 100, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8881.     {name = "irahsae", exp = 0, hp = 1, ratio = 0.000, maxdmg = 900, deathmod = 200, firemod = 100, energymod = 0, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8882.     {name = "island troll", exp = 20, hp = 50, ratio = 0.400, maxdmg = 10, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8883.     {name = "jagged earth elemental", exp = 1300, hp = 1500, ratio = 0.867, maxdmg = 750, deathmod = 55, firemod = 115, energymod = 15, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8884.     {name = "juggernaut", exp = 8700, hp = 20000, ratio = 0.435, maxdmg = 2260, deathmod = 100, firemod = 70, energymod = 110, earthmod = 80, icemod = 90, holymod = 105, physicalmod = 50},
  8885.     {name = "killer caiman", exp = 800, hp = 1500, ratio = 0.533, maxdmg = 300, deathmod = 100, firemod = 100, energymod = 105, earthmod = 80, icemod = 90, holymod = 100, physicalmod = 95},
  8886.     {name = "killer rabbit", exp = 160, hp = 205, ratio = 0.780, maxdmg = 140, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8887.     {name = "kitty", exp = 0, hp = 1, ratio = 0.000, maxdmg = 117, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8888.     {name = "kongra", exp = 115, hp = 340, ratio = 0.338, maxdmg = 60, deathmod = 105, firemod = 80, energymod = 95, earthmod = 90, icemod = 115, holymod = 100, physicalmod = 100},
  8889.     {name = "kongra", exp = 0, hp = 20000, ratio = 0.000, maxdmg = 90, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8890.     {name = "koshei the deathless", exp = 0, hp = 1, ratio = 0.000, maxdmg = 531, deathmod = 0, firemod = 110, energymod = 10, earthmod = 0, icemod = 80, holymod = 115, physicalmod = 80},
  8891.     {name = "kreebosh the exile", exp = 350, hp = 805, ratio = 0.435, maxdmg = 545, deathmod = 101, firemod = 100, energymod = 45, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8892.     {name = "lancer beetle", exp = 275, hp = 400, ratio = 0.688, maxdmg = 246, deathmod = 50, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8893.     {name = "larva", exp = 44, hp = 70, ratio = 0.629, maxdmg = 36, deathmod = 100, firemod = 110, energymod = 90, earthmod = 0, icemod = 105, holymod = 100, physicalmod = 100},
  8894.     {name = "latrivan", exp = 10000, hp = 25000, ratio = 0.400, maxdmg = 1800, deathmod = 0, firemod = 0, energymod = 99, earthmod = 100, icemod = 101, holymod = 100, physicalmod = 100},
  8895.     {name = "lavahole", exp = 0, hp = 1, ratio = 0.000, maxdmg = 111, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8896.     {name = "lersatio", exp = 2500, hp = 1600, ratio = 1.562, maxdmg = 650, deathmod = 100, firemod = 101, energymod = 100, earthmod = 100, icemod = 100, holymod = 101, physicalmod = 100},
  8897.     {name = "lethal lissy", exp = 500, hp = 1450, ratio = 0.345, maxdmg = 160, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8898.     {name = "leviathan", exp = 5000, hp = 6000, ratio = 0.833, maxdmg = 1471, deathmod = 99, firemod = 70, energymod = 110, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 115},
  8899.     {name = "lich", exp = 900, hp = 880, ratio = 1.023, maxdmg = 500, deathmod = 0, firemod = 100, energymod = 20, earthmod = 0, icemod = 100, holymod = 110, physicalmod = 100},
  8900.     {name = "lion", exp = 30, hp = 80, ratio = 0.375, maxdmg = 40, deathmod = 108, firemod = 100, energymod = 100, earthmod = 80, icemod = 115, holymod = 80, physicalmod = 100},
  8901.     {name = "lizard abomination", exp = 1350, hp = 20000, ratio = 0.068, maxdmg = 1500, deathmod = 100, firemod = 110, energymod = 110, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 85},
  8902.     {name = "lizard chosen", exp = 2200, hp = 3050, ratio = 0.721, maxdmg = 880, deathmod = 100, firemod = 90, energymod = 80, earthmod = 0, icemod = 90, holymod = 100, physicalmod = 100},
  8903.     {name = "lizard dragon priest", exp = 1320, hp = 1450, ratio = 0.910, maxdmg = 240, deathmod = 100, firemod = 55, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8904.     {name = "lizard gate guardian", exp = 2000, hp = 3000, ratio = 0.667, maxdmg = 500, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8905.     {name = "lizard high guard", exp = 1450, hp = 1800, ratio = 0.806, maxdmg = 370, deathmod = 100, firemod = 55, energymod = 100, earthmod = 0, icemod = 110, holymod = 100, physicalmod = 95},
  8906.     {name = "lizard legionnaire", exp = 1100, hp = 1400, ratio = 0.786, maxdmg = 460, deathmod = 100, firemod = 55, energymod = 100, earthmod = 0, icemod = 110, holymod = 100, physicalmod = 100},
  8907.     {name = "lizard magistratus", exp = 200, hp = 1, ratio = 200.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8908.     {name = "lizard noble", exp = 250, hp = 1, ratio = 250.000, maxdmg = 330, deathmod = 100, firemod = 10, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8909.     {name = "lizard sentinel", exp = 110, hp = 265, ratio = 0.415, maxdmg = 115, deathmod = 100, firemod = 110, energymod = 90, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8910.     {name = "lizard snakecharmer", exp = 210, hp = 325, ratio = 0.646, maxdmg = 150, deathmod = 100, firemod = 110, energymod = 80, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 120},
  8911.     {name = "lizard templar", exp = 155, hp = 410, ratio = 0.378, maxdmg = 70, deathmod = 100, firemod = 110, energymod = 80, earthmod = 0, icemod = 90, holymod = 100, physicalmod = 100},
  8912.     {name = "lizard zaogun", exp = 1700, hp = 2955, ratio = 0.575, maxdmg = 721, deathmod = 90, firemod = 55, energymod = 80, earthmod = 0, icemod = 85, holymod = 100, physicalmod = 95},
  8913.     {name = "lord of the elements", exp = 8000, hp = 8000, ratio = 1.000, maxdmg = 715, deathmod = 0, firemod = 70, energymod = 70, earthmod = 55, icemod = 70, holymod = 0, physicalmod = 99},
  8914.     {name = "lost soul", exp = 4000, hp = 5800, ratio = 0.690, maxdmg = 630, deathmod = 0, firemod = 0, energymod = 90, earthmod = 0, icemod = 50, holymod = 120, physicalmod = 100},
  8915.     {name = "mad scientist", exp = 205, hp = 325, ratio = 0.631, maxdmg = 127, deathmod = 105, firemod = 90, energymod = 80, earthmod = 80, icemod = 90, holymod = 80, physicalmod = 100},
  8916.     {name = "mad sheep", exp = 0, hp = 22, ratio = 0.000, maxdmg = 1, deathmod = 100, firemod = 101, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8917.     {name = "mad technomancer", exp = 55, hp = 1800, ratio = 0.031, maxdmg = 350, deathmod = 100, firemod = 0, energymod = 105, earthmod = 0, icemod = 101, holymod = 100, physicalmod = 100},
  8918.     {name = "madareth", exp = 10000, hp = 75000, ratio = 0.133, maxdmg = 3359, deathmod = 5, firemod = 101, energymod = 1, earthmod = 100, icemod = 99, holymod = 100, physicalmod = 100},
  8919.     {name = "magic pillar", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8920.     {name = "magicthrower", exp = 0, hp = 1, ratio = 0.000, maxdmg = 100, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8921.     {name = "mahrdis", exp = 3050, hp = 3900, ratio = 0.782, maxdmg = 2400, deathmod = 0, firemod = 0, energymod = 80, earthmod = 80, icemod = 110, holymod = 120, physicalmod = 100},
  8922.     {name = "mammoth", exp = 160, hp = 320, ratio = 0.500, maxdmg = 110, deathmod = 100, firemod = 110, energymod = 100, earthmod = 80, icemod = 80, holymod = 100, physicalmod = 85},
  8923.     {name = "man in the cave", exp = 770, hp = 485, ratio = 1.588, maxdmg = 157, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8924.     {name = "marid", exp = 410, hp = 550, ratio = 0.745, maxdmg = 600, deathmod = 101, firemod = 10, energymod = 40, earthmod = 99, icemod = 101, holymod = 99, physicalmod = 100},
  8925.     {name = "marziel", exp = 3000, hp = 1900, ratio = 1.579, maxdmg = 800, deathmod = 0, firemod = 90, energymod = 80, earthmod = 0, icemod = 105, holymod = 105, physicalmod = 57},
  8926.     {name = "massacre", exp = 20000, hp = 32000, ratio = 0.625, maxdmg = 2800, deathmod = 110, firemod = 0, energymod = 100, earthmod = 100, icemod = 90, holymod = 100, physicalmod = 100},
  8927.     {name = "massive earth elemental", exp = 950, hp = 1330, ratio = 0.714, maxdmg = 438, deathmod = 55, firemod = 115, energymod = 10, earthmod = 0, icemod = 0, holymod = 50, physicalmod = 70},
  8928.     {name = "massive energy elemental", exp = 950, hp = 1100, ratio = 0.864, maxdmg = 1050, deathmod = 99, firemod = 0, energymod = 0, earthmod = 105, icemod = 0, holymod = 75, physicalmod = 30},
  8929.     {name = "massive fire elemental", exp = 1400, hp = 1200, ratio = 1.167, maxdmg = 0, deathmod = 80, firemod = 0, energymod = 70, earthmod = 100, icemod = 115, holymod = 100, physicalmod = 60},
  8930.     {name = "massive water elemental", exp = 1100, hp = 1250, ratio = 0.880, maxdmg = 431, deathmod = 50, firemod = 0, energymod = 125, earthmod = 0, icemod = 0, holymod = 70, physicalmod = 70},
  8931.     {name = "mechanical fighter", exp = 255, hp = 420, ratio = 0.607, maxdmg = 200, deathmod = 100, firemod = 100, energymod = 50, earthmod = 0, icemod = 100, holymod = 0, physicalmod = 100},
  8932.     {name = "medusa", exp = 4050, hp = 4500, ratio = 0.900, maxdmg = 1000, deathmod = 100, firemod = 105, energymod = 110, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8933.     {name = "menace", exp = 4112, hp = 5960, ratio = 0.690, maxdmg = 215, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8934.     {name = "mephiles", exp = 415, hp = 415, ratio = 1.000, maxdmg = 80, deathmod = 100, firemod = 0, energymod = 100, earthmod = 50, icemod = 110, holymod = 105, physicalmod = 110},
  8935.     {name = "mercury blob", exp = 180, hp = 150, ratio = 1.200, maxdmg = 105, deathmod = 0, firemod = 90, energymod = 100, earthmod = 35, icemod = 85, holymod = 35, physicalmod = 95},
  8936.     {name = "merikh the slaughterer", exp = 1500, hp = 2000, ratio = 0.750, maxdmg = 700, deathmod = 99, firemod = 99, energymod = 100, earthmod = 100, icemod = 101, holymod = 101, physicalmod = 100},
  8937.     {name = "merlkin", exp = 145, hp = 235, ratio = 0.617, maxdmg = 170, deathmod = 105, firemod = 80, energymod = 90, earthmod = 100, icemod = 115, holymod = 90, physicalmod = 100},
  8938.     {name = "merlkin", exp = 900, hp = 20000, ratio = 0.045, maxdmg = 10, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8939.     {name = "midnight spawn", exp = 900, hp = 1, ratio = 900.000, maxdmg = 0, deathmod = 1, firemod = 70, energymod = 100, earthmod = 1, icemod = 110, holymod = 110, physicalmod = 70},
  8940.     {name = "midnight warrior", exp = 750, hp = 1000, ratio = 0.750, maxdmg = 250, deathmod = 100, firemod = 110, energymod = 80, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 85},
  8941.     {name = "mimic", exp = 0, hp = 30, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8942.     {name = "minishabaal", exp = 4000, hp = 6000, ratio = 0.667, maxdmg = 800, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8943.     {name = "minotaur", exp = 50, hp = 100, ratio = 0.500, maxdmg = 45, deathmod = 105, firemod = 80, energymod = 100, earthmod = 100, icemod = 110, holymod = 90, physicalmod = 100},
  8944.     {name = "minotaur archer", exp = 65, hp = 100, ratio = 0.650, maxdmg = 100, deathmod = 101, firemod = 80, energymod = 100, earthmod = 100, icemod = 110, holymod = 90, physicalmod = 100},
  8945.     {name = "minotaur guard", exp = 160, hp = 185, ratio = 0.865, maxdmg = 100, deathmod = 110, firemod = 80, energymod = 100, earthmod = 100, icemod = 110, holymod = 90, physicalmod = 100},
  8946.     {name = "minotaur mage", exp = 150, hp = 155, ratio = 0.968, maxdmg = 205, deathmod = 110, firemod = 100, energymod = 80, earthmod = 80, icemod = 110, holymod = 90, physicalmod = 100},
  8947.     {name = "monk", exp = 200, hp = 240, ratio = 0.833, maxdmg = 140, deathmod = 50, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 50, physicalmod = 110},
  8948.     {name = "monstor", exp = 575, hp = 960, ratio = 0.599, maxdmg = 248, deathmod = 100, firemod = 50, energymod = 107, earthmod = 70, icemod = 90, holymod = 103, physicalmod = 80},
  8949.     {name = "mooh'tah master", exp = 0, hp = 1, ratio = 0.000, maxdmg = 700, deathmod = 80, firemod = 70, energymod = 70, earthmod = 0, icemod = 100, holymod = 60, physicalmod = 99},
  8950.     {name = "morgaroth", exp = 15000, hp = 55000, ratio = 0.273, maxdmg = 3500, deathmod = 20, firemod = 0, energymod = 99, earthmod = 0, icemod = 105, holymod = 100, physicalmod = 99},
  8951.     {name = "morguthis", exp = 3000, hp = 4800, ratio = 0.625, maxdmg = 1900, deathmod = 0, firemod = 80, energymod = 80, earthmod = 110, icemod = 80, holymod = 120, physicalmod = 80},
  8952.     {name = "morik the gladiator", exp = 160, hp = 1235, ratio = 0.130, maxdmg = 310, deathmod = 101, firemod = 90, energymod = 90, earthmod = 90, icemod = 90, holymod = 90, physicalmod = 100},
  8953.     {name = "mr. punish", exp = 9000, hp = 22000, ratio = 0.409, maxdmg = 1807, deathmod = 110, firemod = 0, energymod = 0, earthmod = 105, icemod = 0, holymod = 100, physicalmod = 100},
  8954.     {name = "muddy earth elemental", exp = 450, hp = 650, ratio = 0.692, maxdmg = 450, deathmod = 60, firemod = 115, energymod = 15, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  8955.     {name = "mummy", exp = 150, hp = 240, ratio = 0.625, maxdmg = 129, deathmod = 0, firemod = 100, energymod = 100, earthmod = 0, icemod = 80, holymod = 125, physicalmod = 100},
  8956.     {name = "munster", exp = 35, hp = 58, ratio = 0.603, maxdmg = 15, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8957.     {name = "mutated bat", exp = 615, hp = 900, ratio = 0.683, maxdmg = 462, deathmod = 0, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8958.     {name = "mutated human", exp = 150, hp = 240, ratio = 0.625, maxdmg = 164, deathmod = 0, firemod = 100, energymod = 100, earthmod = 0, icemod = 80, holymod = 125, physicalmod = 100},
  8959.     {name = "mutated rat", exp = 450, hp = 550, ratio = 0.818, maxdmg = 305, deathmod = 0, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 90, physicalmod = 100},
  8960.     {name = "mutated tiger", exp = 750, hp = 1100, ratio = 0.682, maxdmg = 275, deathmod = 105, firemod = 80, energymod = 80, earthmod = 20, icemod = 80, holymod = 100, physicalmod = 100},
  8961.     {name = "mutated zalamon", exp = 0, hp = 25000, ratio = 0.000, maxdmg = 1200, deathmod = 100, firemod = 110, energymod = 110, earthmod = 0, icemod = 90, holymod = 100, physicalmod = 95},
  8962.     {name = "necromancer", exp = 580, hp = 580, ratio = 1.000, maxdmg = 260, deathmod = 50, firemod = 105, energymod = 80, earthmod = 0, icemod = 100, holymod = 105, physicalmod = 105},
  8963.     {name = "necropharus", exp = 1050, hp = 750, ratio = 1.400, maxdmg = 300, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8964.     {name = "nightmare", exp = 2150, hp = 2700, ratio = 0.796, maxdmg = 750, deathmod = 0, firemod = 80, energymod = 80, earthmod = 0, icemod = 90, holymod = 125, physicalmod = 100},
  8965.     {name = "nightmare scion", exp = 1350, hp = 1400, ratio = 0.964, maxdmg = 420, deathmod = 0, firemod = 80, energymod = 80, earthmod = 0, icemod = 90, holymod = 125, physicalmod = 100},
  8966.     {name = "nightslayer", exp = 250, hp = 400, ratio = 0.625, maxdmg = 0, deathmod = 0, firemod = 0, energymod = 100, earthmod = 100, icemod = 110, holymod = 100, physicalmod = 105},
  8967.     {name = "nightstalker", exp = 500, hp = 700, ratio = 0.714, maxdmg = 260, deathmod = 105, firemod = 100, energymod = 105, earthmod = 100, icemod = 80, holymod = 80, physicalmod = 105},
  8968.     {name = "nomad", exp = 60, hp = 160, ratio = 0.375, maxdmg = 80, deathmod = 120, firemod = 80, energymod = 100, earthmod = 100, icemod = 110, holymod = 80, physicalmod = 110},
  8969.     {name = "norgle glacierbeard", exp = 2100, hp = 4300, ratio = 0.488, maxdmg = 400, deathmod = 101, firemod = 100, energymod = 110, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 100},
  8970.     {name = "novice of the cult", exp = 100, hp = 285, ratio = 0.351, maxdmg = 270, deathmod = 108, firemod = 105, energymod = 108, earthmod = 90, icemod = 90, holymod = 90, physicalmod = 120},
  8971.     {name = "omruc", exp = 2950, hp = 4300, ratio = 0.686, maxdmg = 1619, deathmod = 0, firemod = 80, energymod = 105, earthmod = 80, icemod = 105, holymod = 110, physicalmod = 100},
  8972.     {name = "orc", exp = 25, hp = 70, ratio = 0.357, maxdmg = 35, deathmod = 101, firemod = 100, energymod = 80, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  8973.     {name = "orc berserker", exp = 195, hp = 210, ratio = 0.929, maxdmg = 200, deathmod = 110, firemod = 100, energymod = 85, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  8974.     {name = "orc leader", exp = 270, hp = 450, ratio = 0.600, maxdmg = 255, deathmod = 101, firemod = 0, energymod = 80, earthmod = 110, icemod = 100, holymod = 80, physicalmod = 100},
  8975.     {name = "orc marauder", exp = 205, hp = 235, ratio = 0.872, maxdmg = 80, deathmod = 100, firemod = 100, energymod = 100, earthmod = 101, icemod = 100, holymod = 99, physicalmod = 100},
  8976.     {name = "orc rider", exp = 110, hp = 180, ratio = 0.611, maxdmg = 120, deathmod = 101, firemod = 100, energymod = 80, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  8977.     {name = "orc shaman", exp = 110, hp = 115, ratio = 0.957, maxdmg = 81, deathmod = 105, firemod = 100, energymod = 50, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  8978.     {name = "orc spearman", exp = 38, hp = 105, ratio = 0.362, maxdmg = 55, deathmod = 110, firemod = 100, energymod = 80, earthmod = 110, icemod = 100, holymod = 80, physicalmod = 100},
  8979.     {name = "orc warlord", exp = 670, hp = 950, ratio = 0.705, maxdmg = 450, deathmod = 105, firemod = 20, energymod = 80, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  8980.     {name = "orc warrior", exp = 50, hp = 125, ratio = 0.400, maxdmg = 60, deathmod = 110, firemod = 100, energymod = 70, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  8981.     {name = "orchid frog", exp = 20, hp = 60, ratio = 0.333, maxdmg = 24, deathmod = 100, firemod = 110, energymod = 100, earthmod = 100, icemod = 90, holymod = 100, physicalmod = 100},
  8982.     {name = "orcus the cruel", exp = 280, hp = 480, ratio = 0.583, maxdmg = 250, deathmod = 100, firemod = 0, energymod = 80, earthmod = 120, icemod = 100, holymod = 100, physicalmod = 100},
  8983.     {name = "orshabaal", exp = 10000, hp = 20500, ratio = 0.488, maxdmg = 5000, deathmod = 50, firemod = 0, energymod = 100, earthmod = 0, icemod = 101, holymod = 101, physicalmod = 100},
  8984.     {name = "overcharged energy element", exp = 1300, hp = 1750, ratio = 0.743, maxdmg = 895, deathmod = 100, firemod = 0, energymod = 0, earthmod = 120, icemod = 0, holymod = 100, physicalmod = 100},
  8985.     {name = "panda", exp = 23, hp = 80, ratio = 0.287, maxdmg = 16, deathmod = 100, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  8986.     {name = "parrot", exp = 0, hp = 25, ratio = 0.000, maxdmg = 5, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8987.     {name = "penguin", exp = 1, hp = 33, ratio = 0.030, maxdmg = 3, deathmod = 100, firemod = 100, energymod = 101, earthmod = 100, icemod = 99, holymod = 100, physicalmod = 100},
  8988.     {name = "phantasm", exp = 4400, hp = 3950, ratio = 1.114, maxdmg = 800, deathmod = 0, firemod = 110, energymod = 110, earthmod = 80, icemod = 80, holymod = 110, physicalmod = 0},
  8989.     {name = "phrodomo", exp = 44000, hp = 80000, ratio = 0.550, maxdmg = 2000, deathmod = 70, firemod = 100, energymod = 0, earthmod = 0, icemod = 50, holymod = 100, physicalmod = 80},
  8990.     {name = "pig", exp = 0, hp = 25, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  8991.     {name = "pillar", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  8992.     {name = "pirate buccaneer", exp = 250, hp = 425, ratio = 0.588, maxdmg = 260, deathmod = 101, firemod = 105, energymod = 105, earthmod = 90, icemod = 105, holymod = 90, physicalmod = 110},
  8993.     {name = "pirate corsair", exp = 350, hp = 675, ratio = 0.519, maxdmg = 320, deathmod = 101, firemod = 110, energymod = 100, earthmod = 80, icemod = 105, holymod = 90, physicalmod = 100},
  8994.     {name = "pirate cutthroat", exp = 175, hp = 325, ratio = 0.538, maxdmg = 271, deathmod = 101, firemod = 110, energymod = 100, earthmod = 90, icemod = 105, holymod = 80, physicalmod = 100},
  8995.     {name = "pirate ghost", exp = 250, hp = 275, ratio = 0.909, maxdmg = 240, deathmod = 0, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 125, physicalmod = 0},
  8996.     {name = "pirate marauder", exp = 125, hp = 210, ratio = 0.595, maxdmg = 180, deathmod = 105, firemod = 110, energymod = 103, earthmod = 90, icemod = 100, holymod = 80, physicalmod = 100},
  8997.     {name = "pirate skeleton", exp = 85, hp = 190, ratio = 0.447, maxdmg = 50, deathmod = 0, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 125, physicalmod = 100},
  8998.     {name = "plaguesmith", exp = 4500, hp = 8250, ratio = 0.545, maxdmg = 890, deathmod = 99, firemod = 70, energymod = 110, earthmod = 0, icemod = 80, holymod = 110, physicalmod = 100},
  8999.     {name = "plaguethrower", exp = 0, hp = 1, ratio = 0.000, maxdmg = 100, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  9000.     {name = "poacher", exp = 70, hp = 90, ratio = 0.778, maxdmg = 70, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9001.     {name = "poison spider", exp = 22, hp = 26, ratio = 0.846, maxdmg = 22, deathmod = 100, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  9002.     {name = "polar bear", exp = 28, hp = 85, ratio = 0.329, maxdmg = 30, deathmod = 110, firemod = 99, energymod = 101, earthmod = 100, icemod = 80, holymod = 100, physicalmod = 100},
  9003.     {name = "priestess", exp = 420, hp = 390, ratio = 1.077, maxdmg = 195, deathmod = 99, firemod = 60, energymod = 100, earthmod = 30, icemod = 100, holymod = 110, physicalmod = 105},
  9004.     {name = "primitive", exp = 45, hp = 200, ratio = 0.225, maxdmg = 90, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9005.     {name = "pythius the rotten", exp = 7000, hp = 9000, ratio = 0.778, maxdmg = 1250, deathmod = 0, firemod = 100, energymod = 0, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  9006.     {name = "quara constrictor", exp = 250, hp = 450, ratio = 0.556, maxdmg = 256, deathmod = 100, firemod = 0, energymod = 125, earthmod = 110, icemod = 0, holymod = 100, physicalmod = 100},
  9007.     {name = "quara constrictor scout", exp = 200, hp = 450, ratio = 0.444, maxdmg = 205, deathmod = 100, firemod = 0, energymod = 110, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 105},
  9008.     {name = "quara hydromancer", exp = 800, hp = 1100, ratio = 0.727, maxdmg = 825, deathmod = 100, firemod = 0, energymod = 125, earthmod = 110, icemod = 0, holymod = 100, physicalmod = 100},
  9009.     {name = "quara hydromancer scout", exp = 800, hp = 1100, ratio = 0.727, maxdmg = 670, deathmod = 100, firemod = 0, energymod = 110, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 100},
  9010.     {name = "quara mantassin", exp = 400, hp = 800, ratio = 0.500, maxdmg = 140, deathmod = 100, firemod = 0, energymod = 125, earthmod = 110, icemod = 0, holymod = 100, physicalmod = 100},
  9011.     {name = "quara mantassin scout", exp = 100, hp = 220, ratio = 0.455, maxdmg = 110, deathmod = 100, firemod = 0, energymod = 110, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 100},
  9012.     {name = "quara pincher", exp = 1200, hp = 1800, ratio = 0.667, maxdmg = 340, deathmod = 100, firemod = 0, energymod = 125, earthmod = 110, icemod = 0, holymod = 100, physicalmod = 90},
  9013.     {name = "quara pincher scout", exp = 600, hp = 775, ratio = 0.774, maxdmg = 240, deathmod = 100, firemod = 0, energymod = 110, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 90},
  9014.     {name = "quara predator", exp = 1600, hp = 2200, ratio = 0.727, maxdmg = 470, deathmod = 100, firemod = 0, energymod = 125, earthmod = 110, icemod = 0, holymod = 100, physicalmod = 100},
  9015.     {name = "quara predator scout", exp = 400, hp = 890, ratio = 0.449, maxdmg = 190, deathmod = 100, firemod = 0, energymod = 110, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 100},
  9016.     {name = "rabbit", exp = 0, hp = 15, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9017.     {name = "rahemos", exp = 3100, hp = 3700, ratio = 0.838, maxdmg = 1850, deathmod = 0, firemod = 5, energymod = 5, earthmod = 0, icemod = 0, holymod = 101, physicalmod = 140},
  9018.     {name = "rat", exp = 5, hp = 20, ratio = 0.250, maxdmg = 8, deathmod = 110, firemod = 100, energymod = 100, earthmod = 75, icemod = 110, holymod = 90, physicalmod = 100},
  9019.     {name = "renegade orc", exp = 270, hp = 450, ratio = 0.600, maxdmg = 180, deathmod = 100, firemod = 0, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9020.     {name = "rift brood", exp = 1600, hp = 3000, ratio = 0.533, maxdmg = 270, deathmod = 120, firemod = 0, energymod = 100, earthmod = 100, icemod = 0, holymod = 85, physicalmod = 99},
  9021.     {name = "rift lord", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9022.     {name = "rift phantom", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9023.     {name = "rift scythe", exp = 2000, hp = 3600, ratio = 0.556, maxdmg = 1000, deathmod = 99, firemod = 110, energymod = 110, earthmod = 60, icemod = 35, holymod = 110, physicalmod = 99},
  9024.     {name = "rift worm", exp = 1195, hp = 2800, ratio = 0.427, maxdmg = 0, deathmod = 100, firemod = 105, energymod = 100, earthmod = 125, icemod = 105, holymod = 105, physicalmod = 100},
  9025.     {name = "roaring water elemental", exp = 1300, hp = 1750, ratio = 0.743, maxdmg = 762, deathmod = 99, firemod = 0, energymod = 100, earthmod = 0, icemod = 0, holymod = 60, physicalmod = 55},
  9026.     {name = "rocko", exp = 3400, hp = 10000, ratio = 0.340, maxdmg = 600, deathmod = 0, firemod = 70, energymod = 75, earthmod = 0, icemod = 80, holymod = 90, physicalmod = 85},
  9027.     {name = "rocky", exp = 190, hp = 390, ratio = 0.487, maxdmg = 80, deathmod = 100, firemod = 101, energymod = 0, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  9028.     {name = "ron the ripper", exp = 500, hp = 1500, ratio = 0.333, maxdmg = 410, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9029.     {name = "rottie the rotworm", exp = 40, hp = 65, ratio = 0.615, maxdmg = 25, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9030.     {name = "rotworm", exp = 40, hp = 65, ratio = 0.615, maxdmg = 40, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9031.     {name = "rotworm queen", exp = 75, hp = 105, ratio = 0.714, maxdmg = 80, deathmod = 100, firemod = 120, energymod = 100, earthmod = 60, icemod = 100, holymod = 100, physicalmod = 100},
  9032.     {name = "rukor zad", exp = 380, hp = 380, ratio = 1.000, maxdmg = 370, deathmod = 95, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 99},
  9033.     {name = "sandcrawler", exp = 20, hp = 30, ratio = 0.667, maxdmg = 3, deathmod = 100, firemod = 101, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9034.     {name = "scarab", exp = 120, hp = 320, ratio = 0.375, maxdmg = 115, deathmod = 100, firemod = 118, energymod = 90, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 85},
  9035.     {name = "scorn of the emperor", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 90, energymod = 110, earthmod = 0, icemod = 50, holymod = 115, physicalmod = 110},
  9036.     {name = "scorpion", exp = 45, hp = 45, ratio = 1.000, maxdmg = 67, deathmod = 100, firemod = 110, energymod = 80, earthmod = 0, icemod = 110, holymod = 100, physicalmod = 100},
  9037.     {name = "sea serpent", exp = 2300, hp = 1950, ratio = 1.179, maxdmg = 800, deathmod = 90, firemod = 70, energymod = 105, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 115},
  9038.     {name = "seagull", exp = 0, hp = 25, ratio = 0.000, maxdmg = 3, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9039.     {name = "serpent spawn", exp = 3050, hp = 3000, ratio = 1.017, maxdmg = 1400, deathmod = 100, firemod = 110, energymod = 110, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  9040.     {name = "servant golem", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  9041.     {name = "shadow hound", exp = 600, hp = 555, ratio = 1.081, maxdmg = 155, deathmod = 0, firemod = 110, energymod = 90, earthmod = 0, icemod = 110, holymod = 70, physicalmod = 120},
  9042.     {name = "shadow of boreth", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9043.     {name = "shadow of lersatio", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9044.     {name = "shadow of marziel", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9045.     {name = "shard of corruption", exp = 5, hp = 600, ratio = 0.008, maxdmg = 200, deathmod = 0, firemod = 70, energymod = 75, earthmod = 0, icemod = 85, holymod = 100, physicalmod = 40},
  9046.     {name = "shardhead", exp = 650, hp = 800, ratio = 0.812, maxdmg = 300, deathmod = 0, firemod = 100, energymod = 120, earthmod = 100, icemod = 100, holymod = 0, physicalmod = 100},
  9047.     {name = "sharptooth", exp = 1600, hp = 2500, ratio = 0.640, maxdmg = 500, deathmod = 100, firemod = 0, energymod = 105, earthmod = 20, icemod = 100, holymod = 100, physicalmod = 100},
  9048.     {name = "sheep", exp = 0, hp = 20, ratio = 0.000, maxdmg = 1, deathmod = 100, firemod = 101, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9049.     {name = "shredderthrower", exp = 0, hp = 1, ratio = 0.000, maxdmg = 110, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  9050.     {name = "sibang", exp = 105, hp = 225, ratio = 0.467, maxdmg = 95, deathmod = 105, firemod = 75, energymod = 100, earthmod = 100, icemod = 115, holymod = 90, physicalmod = 100},
  9051.     {name = "silver rabbit", exp = 0, hp = 15, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9052.     {name = "sir valorcrest", exp = 1800, hp = 1600, ratio = 1.125, maxdmg = 670, deathmod = 0, firemod = 101, energymod = 100, earthmod = 100, icemod = 100, holymod = 105, physicalmod = 45},
  9053.     {name = "skeleton", exp = 35, hp = 50, ratio = 0.700, maxdmg = 30, deathmod = 0, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 101, physicalmod = 100},
  9054.     {name = "skeleton warrior", exp = 45, hp = 65, ratio = 0.692, maxdmg = 43, deathmod = 0, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 101, physicalmod = 100},
  9055.     {name = "skunk", exp = 3, hp = 20, ratio = 0.150, maxdmg = 8, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9056.     {name = "slick water elemental", exp = 450, hp = 550, ratio = 0.818, maxdmg = 542, deathmod = 99, firemod = 0, energymod = 100, earthmod = 0, icemod = 0, holymod = 60, physicalmod = 55},
  9057.     {name = "slim", exp = 580, hp = 1025, ratio = 0.566, maxdmg = 250, deathmod = 0, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 101, physicalmod = 100},
  9058.     {name = "slime", exp = 160, hp = 150, ratio = 1.067, maxdmg = 107, deathmod = 100, firemod = 110, energymod = 110, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  9059.     {name = "slime puddle", exp = 0, hp = 1, ratio = 0.000, maxdmg = 120, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9060.     {name = "smuggler", exp = 48, hp = 130, ratio = 0.369, maxdmg = 60, deathmod = 105, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 105},
  9061.     {name = "smuggler baron silvertoe", exp = 170, hp = 280, ratio = 0.607, maxdmg = 41, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9062.     {name = "snake", exp = 10, hp = 15, ratio = 0.667, maxdmg = 9, deathmod = 100, firemod = 110, energymod = 80, earthmod = 0, icemod = 110, holymod = 100, physicalmod = 100},
  9063.     {name = "snake god essence", exp = 1350, hp = 20000, ratio = 0.068, maxdmg = 1000, deathmod = 100, firemod = 110, energymod = 110, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 90},
  9064.     {name = "snake thing", exp = 4600, hp = 20000, ratio = 0.230, maxdmg = 1000, deathmod = 100, firemod = 110, energymod = 110, earthmod = 0, icemod = 90, holymod = 100, physicalmod = 100},
  9065.     {name = "son of verminor", exp = 5900, hp = 8500, ratio = 0.694, maxdmg = 1000, deathmod = 100, firemod = 90, energymod = 80, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  9066.     {name = "souleater", exp = 1300, hp = 1100, ratio = 1.182, maxdmg = 480, deathmod = 0, firemod = 110, energymod = 110, earthmod = 100, icemod = 50, holymod = 110, physicalmod = 30},
  9067.     {name = "spawn of despair", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 60, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9068.     {name = "spawn of devovorga", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9069.     {name = "spectral scum", exp = 0, hp = 1, ratio = 0.000, maxdmg = 120, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9070.     {name = "spectre", exp = 2100, hp = 1350, ratio = 1.556, maxdmg = 820, deathmod = 0, firemod = 108, energymod = 108, earthmod = 0, icemod = 99, holymod = 100, physicalmod = 10},
  9071.     {name = "spider", exp = 12, hp = 20, ratio = 0.600, maxdmg = 25, deathmod = 100, firemod = 101, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9072.     {name = "spirit of earth", exp = 800, hp = 1294, ratio = 0.618, maxdmg = 640, deathmod = 100, firemod = 110, energymod = 50, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9073.     {name = "spirit of fire", exp = 950, hp = 2210, ratio = 0.430, maxdmg = 640, deathmod = 100, firemod = 0, energymod = 80, earthmod = 100, icemod = 101, holymod = 100, physicalmod = 100},
  9074.     {name = "spirit of light", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  9075.     {name = "spirit of water", exp = 850, hp = 1517, ratio = 0.560, maxdmg = 995, deathmod = 100, firemod = 0, energymod = 110, earthmod = 100, icemod = 0, holymod = 50, physicalmod = 70},
  9076.     {name = "spit nettle", exp = 20, hp = 150, ratio = 0.133, maxdmg = 45, deathmod = 100, firemod = 110, energymod = 0, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  9077.     {name = "spite of the emperor", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 90, energymod = 110, earthmod = 0, icemod = 50, holymod = 115, physicalmod = 110},
  9078.     {name = "splasher", exp = 500, hp = 1000, ratio = 0.500, maxdmg = 808, deathmod = 100, firemod = 0, energymod = 125, earthmod = 115, icemod = 0, holymod = 100, physicalmod = 100},
  9079.     {name = "squirrel", exp = 0, hp = 20, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9080.     {name = "stalker", exp = 90, hp = 120, ratio = 0.750, maxdmg = 100, deathmod = 99, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 105, physicalmod = 120},
  9081.     {name = "stampor", exp = 780, hp = 1200, ratio = 0.650, maxdmg = 350, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9082.     {name = "stone golem", exp = 160, hp = 270, ratio = 0.593, maxdmg = 110, deathmod = 80, firemod = 80, energymod = 85, earthmod = 0, icemod = 110, holymod = 100, physicalmod = 80},
  9083.     {name = "stonecracker", exp = 3500, hp = 5500, ratio = 0.636, maxdmg = 840, deathmod = 100, firemod = 100, energymod = 70, earthmod = 25, icemod = 100, holymod = 99, physicalmod = 99},
  9084.     {name = "svoren the mad", exp = 3000, hp = 6300, ratio = 0.476, maxdmg = 550, deathmod = 100, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 100, physicalmod = 100},
  9085.     {name = "swamp troll", exp = 25, hp = 55, ratio = 0.455, maxdmg = 14, deathmod = 100, firemod = 101, energymod = 100, earthmod = 99, icemod = 100, holymod = 100, physicalmod = 100},
  9086.     {name = "tarantula", exp = 120, hp = 225, ratio = 0.533, maxdmg = 90, deathmod = 100, firemod = 115, energymod = 90, earthmod = 0, icemod = 110, holymod = 100, physicalmod = 100},
  9087.     {name = "target dummy", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 5, firemod = 5, energymod = 5, earthmod = 5, icemod = 5, holymod = 5, physicalmod = 30},
  9088.     {name = "teleskor", exp = 70, hp = 80, ratio = 0.875, maxdmg = 30, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9089.     {name = "teneshpar", exp = 0, hp = 1, ratio = 0.000, maxdmg = 800, deathmod = 0, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 0},
  9090.     {name = "terramite", exp = 160, hp = 365, ratio = 0.438, maxdmg = 116, deathmod = 100, firemod = 110, energymod = 105, earthmod = 80, icemod = 100, holymod = 100, physicalmod = 95},
  9091.     {name = "terror bird", exp = 150, hp = 300, ratio = 0.500, maxdmg = 90, deathmod = 105, firemod = 110, energymod = 80, earthmod = 110, icemod = 80, holymod = 100, physicalmod = 100},
  9092.     {name = "thalas", exp = 2950, hp = 4100, ratio = 0.720, maxdmg = 1400, deathmod = 0, firemod = 110, energymod = 80, earthmod = 0, icemod = 110, holymod = 120, physicalmod = 100},
  9093.     {name = "the abomination", exp = 0, hp = 1, ratio = 0.000, maxdmg = 1300, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9094.     {name = "the axeorcist", exp = 4005, hp = 5100, ratio = 0.785, maxdmg = 706, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9095.     {name = "the big bad one", exp = 170, hp = 300, ratio = 0.567, maxdmg = 100, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9096.     {name = "the blightfather", exp = 600, hp = 400, ratio = 1.500, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  9097.     {name = "the bloodtusk", exp = 300, hp = 600, ratio = 0.500, maxdmg = 120, deathmod = 100, firemod = 110, energymod = 100, earthmod = 85, icemod = 110, holymod = 100, physicalmod = 100},
  9098.     {name = "the collector", exp = 100, hp = 340, ratio = 0.294, maxdmg = 46, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 100},
  9099.     {name = "the count", exp = 450, hp = 1250, ratio = 0.360, maxdmg = 500, deathmod = 0, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 101, physicalmod = 40},
  9100.     {name = "the dark dancer", exp = 435, hp = 855, ratio = 0.509, maxdmg = 90, deathmod = 99, firemod = 60, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9101.     {name = "the dreadorian", exp = 4000, hp = 1, ratio = 4000.000, maxdmg = 388, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9102.     {name = "the evil eye", exp = 750, hp = 1200, ratio = 0.625, maxdmg = 1169, deathmod = 100, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 101, physicalmod = 100},
  9103.     {name = "the frog prince", exp = 1, hp = 55, ratio = 0.018, maxdmg = 1, deathmod = 100, firemod = 90, energymod = 15, earthmod = 100, icemod = 10, holymod = 100, physicalmod = 100},
  9104.     {name = "the hag", exp = 510, hp = 935, ratio = 0.545, maxdmg = 100, deathmod = 100, firemod = 70, energymod = 90, earthmod = 100, icemod = 99, holymod = 100, physicalmod = 100},
  9105.     {name = "the hairy one", exp = 115, hp = 325, ratio = 0.354, maxdmg = 70, deathmod = 100, firemod = 120, energymod = 95, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9106.     {name = "the halloween hare", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  9107.     {name = "the handmaiden", exp = 7500, hp = 1, ratio = 7500.000, maxdmg = 2020, deathmod = 100, firemod = 0, energymod = 85, earthmod = 0, icemod = 85, holymod = 110, physicalmod = 100},
  9108.     {name = "the horned fox", exp = 300, hp = 265, ratio = 1.132, maxdmg = 120, deathmod = 101, firemod = 100, energymod = 100, earthmod = 100, icemod = 101, holymod = 100, physicalmod = 100},
  9109.     {name = "the imperor", exp = 8000, hp = 15000, ratio = 0.533, maxdmg = 2000, deathmod = 100, firemod = 0, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9110.     {name = "the keeper", exp = 3205, hp = 25000, ratio = 0.128, maxdmg = 1400, deathmod = 50, firemod = 110, energymod = 110, earthmod = 0, icemod = 80, holymod = 100, physicalmod = 100},
  9111.     {name = "the many", exp = 4000, hp = 1, ratio = 4000.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9112.     {name = "the masked marauder", exp = 3500, hp = 6800, ratio = 0.515, maxdmg = 930, deathmod = 100, firemod = 0, energymod = 70, earthmod = 100, icemod = 100, holymod = 101, physicalmod = 100},
  9113.     {name = "the mutated pumpkin", exp = 35000, hp = 550000, ratio = 0.064, maxdmg = 300, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9114.     {name = "the noxious spawn", exp = 6000, hp = 9500, ratio = 0.632, maxdmg = 1350, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9115.     {name = "the obliverator", exp = 6000, hp = 9500, ratio = 0.632, maxdmg = 1000, deathmod = 99, firemod = 0, energymod = 50, earthmod = 100, icemod = 100, holymod = 101, physicalmod = 100},
  9116.     {name = "the old whopper", exp = 750, hp = 785, ratio = 0.955, maxdmg = 175, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9117.     {name = "the old widow", exp = 4200, hp = 3200, ratio = 1.312, maxdmg = 1050, deathmod = 100, firemod = 80, energymod = 90, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 80},
  9118.     {name = "the pit lord", exp = 2500, hp = 4500, ratio = 0.556, maxdmg = 568, deathmod = 100, firemod = 100, energymod = 100, earthmod = 99, icemod = 101, holymod = 100, physicalmod = 100},
  9119.     {name = "the plasmother", exp = 8300, hp = 1, ratio = 8300.000, maxdmg = 1000, deathmod = 110, firemod = 100, energymod = 90, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  9120.     {name = "the ruthless herald", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 0, energymod = 0, earthmod = 0, icemod = 0, holymod = 0, physicalmod = 0},
  9121.     {name = "the snapper", exp = 150, hp = 300, ratio = 0.500, maxdmg = 60, deathmod = 100, firemod = 110, energymod = 105, earthmod = 85, icemod = 90, holymod = 100, physicalmod = 105},
  9122.     {name = "the voice of ruin", exp = 3900, hp = 5500, ratio = 0.709, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9123.     {name = "the weakened count", exp = 450, hp = 740, ratio = 0.608, maxdmg = 283, deathmod = 0, firemod = 101, energymod = 100, earthmod = 0, icemod = 100, holymod = 101, physicalmod = 99},
  9124.     {name = "thief", exp = 5, hp = 60, ratio = 0.083, maxdmg = 32, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9125.     {name = "thieving squirrel", exp = 0, hp = 55, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9126.     {name = "thornback tortoise", exp = 150, hp = 300, ratio = 0.500, maxdmg = 112, deathmod = 100, firemod = 110, energymod = 100, earthmod = 80, icemod = 80, holymod = 100, physicalmod = 55},
  9127.     {name = "thul", exp = 2700, hp = 2950, ratio = 0.915, maxdmg = 302, deathmod = 100, firemod = 100, energymod = 101, earthmod = 0, icemod = 0, holymod = 100, physicalmod = 100},
  9128.     {name = "tibia bug", exp = 50, hp = 270, ratio = 0.185, maxdmg = 70, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9129.     {name = "tiger", exp = 40, hp = 75, ratio = 0.533, maxdmg = 40, deathmod = 110, firemod = 100, energymod = 100, earthmod = 100, icemod = 101, holymod = 100, physicalmod = 100},
  9130.     {name = "tiquandas revenge", exp = 2635, hp = 1800, ratio = 1.464, maxdmg = 910, deathmod = 99, firemod = 101, energymod = 100, earthmod = 0, icemod = 99, holymod = 100, physicalmod = 99},
  9131.     {name = "tirecz", exp = 6000, hp = 25000, ratio = 0.240, maxdmg = 1200, deathmod = 70, firemod = 50, energymod = 70, earthmod = 70, icemod = 70, holymod = 70, physicalmod = 90},
  9132.     {name = "toad", exp = 60, hp = 135, ratio = 0.444, maxdmg = 48, deathmod = 100, firemod = 110, energymod = 100, earthmod = 80, icemod = 80, holymod = 100, physicalmod = 100},
  9133.     {name = "tormented ghost", exp = 5, hp = 210, ratio = 0.024, maxdmg = 170, deathmod = 100, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 0},
  9134.     {name = "tortoise", exp = 90, hp = 185, ratio = 0.486, maxdmg = 50, deathmod = 100, firemod = 110, energymod = 100, earthmod = 80, icemod = 80, holymod = 100, physicalmod = 65},
  9135.     {name = "tortoise", exp = 0, hp = 1, ratio = 0.000, maxdmg = 100, deathmod = 100, firemod = 110, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9136.     {name = "tremorak", exp = 1300, hp = 10000, ratio = 0.130, maxdmg = 660, deathmod = 65, firemod = 115, energymod = 15, earthmod = 0, icemod = 80, holymod = 50, physicalmod = 50},
  9137.     {name = "troll", exp = 20, hp = 50, ratio = 0.400, maxdmg = 24, deathmod = 110, firemod = 100, energymod = 75, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  9138.     {name = "troll champion", exp = 40, hp = 75, ratio = 0.533, maxdmg = 35, deathmod = 110, firemod = 100, energymod = 85, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  9139.     {name = "troll legionnaire", exp = 140, hp = 210, ratio = 0.667, maxdmg = 170, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9140.     {name = "undead dragon", exp = 7200, hp = 8350, ratio = 0.862, maxdmg = 1975, deathmod = 0, firemod = 0, energymod = 100, earthmod = 0, icemod = 50, holymod = 125, physicalmod = 95},
  9141.     {name = "undead gladiator", exp = 800, hp = 1000, ratio = 0.800, maxdmg = 385, deathmod = 101, firemod = 20, energymod = 80, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  9142.     {name = "undead jester", exp = 5, hp = 355, ratio = 0.014, maxdmg = 3, deathmod = 0, firemod = 80, energymod = 90, earthmod = 0, icemod = 70, holymod = 120, physicalmod = 100},
  9143.     {name = "undead mine worker", exp = 45, hp = 65, ratio = 0.692, maxdmg = 33, deathmod = 0, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 101, physicalmod = 100},
  9144.     {name = "undead minion", exp = 550, hp = 850, ratio = 0.647, maxdmg = 560, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9145.     {name = "undead prospector", exp = 85, hp = 100, ratio = 0.850, maxdmg = 50, deathmod = 0, firemod = 100, energymod = 70, earthmod = 80, icemod = 90, holymod = 125, physicalmod = 100},
  9146.     {name = "ungreez", exp = 500, hp = 8200, ratio = 0.061, maxdmg = 1500, deathmod = 80, firemod = 0, energymod = 45, earthmod = 40, icemod = 105, holymod = 105, physicalmod = 70},
  9147.     {name = "ushuriel", exp = 10000, hp = 40000, ratio = 0.250, maxdmg = 2600, deathmod = 0, firemod = 70, energymod = 70, earthmod = 70, icemod = 70, holymod = 75, physicalmod = 50},
  9148.     {name = "valkyrie", exp = 85, hp = 190, ratio = 0.447, maxdmg = 120, deathmod = 101, firemod = 90, energymod = 100, earthmod = 100, icemod = 90, holymod = 99, physicalmod = 101},
  9149.     {name = "vampire", exp = 305, hp = 475, ratio = 0.642, maxdmg = 350, deathmod = 0, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 125, physicalmod = 65},
  9150.     {name = "vampire bride", exp = 1050, hp = 1200, ratio = 0.875, maxdmg = 570, deathmod = 0, firemod = 110, energymod = 90, earthmod = 80, icemod = 80, holymod = 110, physicalmod = 100},
  9151.     {name = "vampire pig", exp = 165, hp = 305, ratio = 0.541, maxdmg = 190, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 90},
  9152.     {name = "vashresamun", exp = 2950, hp = 4000, ratio = 0.738, maxdmg = 1300, deathmod = 0, firemod = 80, energymod = 80, earthmod = 80, icemod = 80, holymod = 110, physicalmod = 100},
  9153.     {name = "verminor", exp = 80000, hp = 160000, ratio = 0.500, maxdmg = 601000, deathmod = 100, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  9154.     {name = "vulnerable cocoon", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9155.     {name = "wailing widow", exp = 450, hp = 850, ratio = 0.529, maxdmg = 260, deathmod = 0, firemod = 101, energymod = 100, earthmod = 0, icemod = 100, holymod = 99, physicalmod = 100},
  9156.     {name = "war golem", exp = 2750, hp = 4300, ratio = 0.640, maxdmg = 800, deathmod = 75, firemod = 85, energymod = 95, earthmod = 50, icemod = 70, holymod = 50, physicalmod = 75},
  9157.     {name = "war wolf", exp = 55, hp = 140, ratio = 0.393, maxdmg = 50, deathmod = 101, firemod = 100, energymod = 100, earthmod = 80, icemod = 110, holymod = 90, physicalmod = 100},
  9158.     {name = "warlock", exp = 4000, hp = 3500, ratio = 1.143, maxdmg = 810, deathmod = 100, firemod = 0, energymod = 0, earthmod = 5, icemod = 0, holymod = 101, physicalmod = 101},
  9159.     {name = "warlord ruzad", exp = 1700, hp = 2500, ratio = 0.680, maxdmg = 0, deathmod = 110, firemod = 20, energymod = 99, earthmod = 110, icemod = 100, holymod = 90, physicalmod = 100},
  9160.     {name = "wasp", exp = 24, hp = 35, ratio = 0.686, maxdmg = 20, deathmod = 100, firemod = 110, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 100},
  9161.     {name = "water elemental", exp = 650, hp = 550, ratio = 1.182, maxdmg = 560, deathmod = 50, firemod = 0, energymod = 125, earthmod = 0, icemod = 0, holymod = 50, physicalmod = 50},
  9162.     {name = "weak eclipse knight", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9163.     {name = "weak gloombringer", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9164.     {name = "weak harbinger of darkness", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9165.     {name = "weak spawn of despair", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 100, firemod = 60, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9166.     {name = "webster", exp = 1200, hp = 1750, ratio = 0.686, maxdmg = 270, deathmod = 100, firemod = 100, energymod = 101, earthmod = 100, icemod = 0, holymod = 100, physicalmod = 100},
  9167.     {name = "werewolf", exp = 1900, hp = 1955, ratio = 0.972, maxdmg = 515, deathmod = 99, firemod = 105, energymod = 95, earthmod = 35, icemod = 105, holymod = 105, physicalmod = 90},
  9168.     {name = "wild warrior", exp = 60, hp = 135, ratio = 0.444, maxdmg = 70, deathmod = 105, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 90, physicalmod = 105},
  9169.     {name = "winter wolf", exp = 20, hp = 30, ratio = 0.667, maxdmg = 20, deathmod = 101, firemod = 90, energymod = 101, earthmod = 100, icemod = 80, holymod = 99, physicalmod = 100},
  9170.     {name = "wisp", exp = 0, hp = 115, ratio = 0.000, maxdmg = 7, deathmod = 0, firemod = 100, energymod = 70, earthmod = 10, icemod = 100, holymod = 100, physicalmod = 35},
  9171.     {name = "witch", exp = 120, hp = 300, ratio = 0.400, maxdmg = 115, deathmod = 105, firemod = 100, energymod = 0, earthmod = 80, icemod = 100, holymod = 100, physicalmod = 110},
  9172.     {name = "wolf", exp = 18, hp = 25, ratio = 0.720, maxdmg = 19, deathmod = 101, firemod = 100, energymod = 100, earthmod = 99, icemod = 101, holymod = 99, physicalmod = 100},
  9173.     {name = "worker golem", exp = 1250, hp = 1470, ratio = 0.850, maxdmg = 361, deathmod = 90, firemod = 100, energymod = 105, earthmod = 50, icemod = 90, holymod = 50, physicalmod = 90},
  9174.     {name = "wrath of the emperor", exp = 0, hp = 1, ratio = 0.000, maxdmg = 0, deathmod = 0, firemod = 90, energymod = 110, earthmod = 0, icemod = 50, holymod = 115, physicalmod = 105},
  9175.     {name = "wyrm", exp = 1550, hp = 1825, ratio = 0.849, maxdmg = 500, deathmod = 105, firemod = 80, energymod = 0, earthmod = 25, icemod = 105, holymod = 100, physicalmod = 100},
  9176.     {name = "wyvern", exp = 515, hp = 795, ratio = 0.648, maxdmg = 140, deathmod = 100, firemod = 100, energymod = 80, earthmod = 0, icemod = 90, holymod = 100, physicalmod = 100},
  9177.     {name = "xenia", exp = 255, hp = 200, ratio = 1.275, maxdmg = 50, deathmod = 100, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 100, physicalmod = 100},
  9178.     {name = "yaga the crone", exp = 375, hp = 620, ratio = 0.605, maxdmg = 60, deathmod = 105, firemod = 100, energymod = 0, earthmod = 99, icemod = 100, holymod = 100, physicalmod = 101},
  9179.     {name = "yakchal", exp = 4400, hp = 5000, ratio = 0.880, maxdmg = 1000, deathmod = 100, firemod = 100, energymod = 105, earthmod = 100, icemod = 100, holymod = 50, physicalmod = 100},
  9180.     {name = "yalahari", exp = 5, hp = 150, ratio = 0.033, maxdmg = 0, deathmod = 0, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 0},
  9181.     {name = "yeti", exp = 460, hp = 950, ratio = 0.484, maxdmg = 555, deathmod = 100, firemod = 100, energymod = 100, earthmod = 101, icemod = 100, holymod = 100, physicalmod = 100},
  9182.     {name = "young sea serpent", exp = 1000, hp = 1050, ratio = 0.952, maxdmg = 700, deathmod = 115, firemod = 70, energymod = 110, earthmod = 0, icemod = 0, holymod = 100, physicalmod = 115},
  9183.     {name = "zarabustor", exp = 8000, hp = 5100, ratio = 1.569, maxdmg = 1800, deathmod = 100, firemod = 0, energymod = 0, earthmod = 10, icemod = 0, holymod = 101, physicalmod = 101},
  9184.     {name = "zevelon duskbringer", exp = 1800, hp = 1400, ratio = 1.286, maxdmg = 1000, deathmod = 0, firemod = 100, energymod = 100, earthmod = 0, icemod = 100, holymod = 100, physicalmod = 50},
  9185.     {name = "zombie", exp = 280, hp = 500, ratio = 0.560, maxdmg = 203, deathmod = 0, firemod = 50, energymod = 0, earthmod = 0, icemod = 0, holymod = 100, physicalmod = 100},
  9186.     {name = "zoralurk", exp = 0, hp = 1, ratio = 0.000, maxdmg = 2587, deathmod = 10, firemod = 0, energymod = 40, earthmod = 20, icemod = 50, holymod = 60, physicalmod = 40},
  9187.     {name = "zugurosh", exp = 10000, hp = 95000, ratio = 0.105, maxdmg = 1866, deathmod = 0, firemod = 70, energymod = 80, earthmod = 60, icemod = 75, holymod = 70, physicalmod = 100},
  9188.     {name = "zulazza the corruptor", exp = 9800, hp = 28000, ratio = 0.350, maxdmg = 3700, deathmod = 70, firemod = 100, energymod = 0, earthmod = 30, icemod = 80, holymod = 80, physicalmod = 100},
  9189.     {name = "skeleton", exp = 35, hp = 50, ratio = 0.700, maxdmg = 30, deathmod = 0, firemod = 100, energymod = 100, earthmod = 100, icemod = 100, holymod = 101, physicalmod = 100},
  9190. }
  9191.  
  9192.  
  9193.  
  9194. ------------------------------Anonymickey.lua---------------------------------
  9195.  
  9196.  
  9197. --    #########################################
  9198. --   #      Anonymickey's Library            #
  9199. --  #   Last updated: 10/30 - 01:46 (v1.7)  #
  9200. -- #########################################
  9201.  
  9202. print('Anonymickey\'s Library loaded. Last updated: 10/30 - 01:46 (v1.7)')
  9203. print('Updates: http://forums.tibianeobot.com/showthread.php?2869')
  9204.  
  9205. local skills = {
  9206.             magic = {$mlevelpc, nil, nil, nil, nil, nil, nil},
  9207.             fist = {$fistpc, nil, nil, nil, nil, nil, nil},
  9208.             club = {$clubpc, nil, nil, nil, nil, nil, nil},
  9209.             sword = {$swordpc, nil, nil, nil, nil, nil, nil},
  9210.             axe = {$axepc, nil, nil, nil, nil, nil, nil},
  9211.             distance = {$distancepc, nil, nil, nil, nil, nil, nil},
  9212.             shielding = {$shieldingpc, nil, nil, nil, nil, nil, nil},
  9213.             fishing = {$fishingpc, nil, nil, nil, nil, nil, nil}
  9214.                 }
  9215.  
  9216. function flasks() -- Working
  9217.     return itemcount('empty potion flask (small)') +  itemcount('empty potion flask (medium)') + itemcount('empty potion flask (large)')
  9218. end
  9219.  
  9220. function dropflasks() -- Working
  9221.     local flaskids = {'empty potion flask (small)', 'empty potion flask (medium)', 'empty potion flask (large)'}
  9222.     for i = 1, #flaskids do
  9223.         if itemcount(flaskids[i]) > 0 then
  9224.             dropitems('ground', flaskids[i])
  9225.             wait($ping * 1.4, $ping * 2.3)
  9226.         end
  9227.     end
  9228. end
  9229.  
  9230. function gold() -- Working
  9231.     return itemcount('gold coin') + itemcount('platinum coin') * 100 + itemcount('crystal coin') * 10000
  9232. end
  9233.  
  9234. function moveitemlist(locationto, locationfrom, ...) -- Working
  9235.     local t = {...}
  9236.     for i = 1, #t do
  9237.         if itemcount(t[i], locationfrom or '') > 0 then
  9238.             moveitems(t[i], locationto, locationfrom or '')
  9239.             wait($ping * 1.3, $ping * 2)
  9240.         end
  9241.     end
  9242. end
  9243.  
  9244. function npctalk(...) -- Working
  9245.     local s = 1
  9246.     local t = {...}
  9247.     if not ischannel('NPCs') then
  9248.         s = 2
  9249.         while not ischannel('NPCs') do
  9250.             say('Default', t[1])
  9251.             wait($ping * 4, $ping * 8)
  9252.         end
  9253.     end
  9254.     for i = s, #t do
  9255.         say('NPCs', t[i])
  9256.         wait($ping * 1.4, $ping * 2)
  9257.     end
  9258. end
  9259.  
  9260.  
  9261.  
  9262. function skilltime(skilltype) -- Needs to be remade/adjusted.
  9263.     local percent = {magic = $mlevelpc, fist = $fistpc, club = $clubpc, sword = $swordpc, axe = $axepc, distance = $distancepc, shielding = $shieldingpc, fishing = $fishingpc}
  9264.     local skillpc = percent[skilltype]
  9265.     if skillpc ~= skills[skilltype][1] then
  9266.         if skillpc ~= 0 then
  9267.             if skills[skilltype][3] then
  9268.                 skills[skilltype][2] = ($timems - skills[skilltype][3]) * (100 - skillpc) / (skillpc - skills[skilltype][1])
  9269.             else
  9270.                 skills[skilltype][2] = nil
  9271.             end
  9272.         end
  9273.         skills[skilltype][1] = skillpc
  9274.         skills[skilltype][3] = $timems
  9275.     end
  9276.     if skills[skilltype][2] then
  9277.         return math.max(math.floor((skills[skilltype][2] - ($timems - skills[skilltype][3])) / 1000), 0)
  9278.     else
  9279.         return 0
  9280.     end
  9281. end
  9282.  
  9283. function keyid(key) -- Working -- Find full list at: http://api.farmanager.com/en/winapi/virtualkeycodes.html
  9284.     local keys = {MOUSELEFT = 0x01, MOUSERIGHT = 0x02, MOUSEMIDDLE = 0x04, BACKSPACE = 0x08, TAB = 0x09, CLEAR = 0x0C, ENTER = 0x0D, SHIFT = 0x10, CTRL = 0x11, ALT = 0x12, PAUSE = 0x13, CAPSLOCK = 0x14, ESC = 0x1B, SPACE = 0x20, PAGEUP = 0x21, PAGEDOWN = 0x22, END = 0x25, HOME = 0x24, LEFTARROW = 0x25, UPARROW = 0x26, RIGHTARROW = 0x27, DOWNARROW = 0x28, SELECT = 0x29, PRINT = 0x2A, ExECUTE = 0x2B, PRINTSCREEN =0x2C, INSERT = 0x2D, DELETE = 0x2E, HELP = 0x2F, A = 0x41, B = 0x42, C = 0x43, D = 0x44, E = 0x45, F = 0x46, G = 0x47, H = 0x48, I = 0x49, J = 0x4A, K = 0x4B, L = 0x4C, M = 0x4D, N = 0x4E, O = 0x4F, P = 0x50, Q = 0x51, R = 0x52, S = 0x53, T = 0x54, U = 0x55, V = 0x56, W = 0x57, x = 0x58, Y = 0x59, Z = 0x5A, SLEEP = 0x5F, NUM0 = 0x60, NUM1 = 0x61, NUM2 = 0x62, NUM3 = 0x63, NUM4 = 0x64, NUM5 = 0x65, NUM6 = 0x66, NUM7 = 0x67, NUM8 = 0x68, NUM9 = 0x69, MULTIPLY = 0x6A, ADD = 0x6B, SEPARATOR = 0x6C, SUBTRACT = 0x6D, DECIMAL = 0x6E, DIVIDE = 0x6F, F1 = 0x70, F2 = 0x71, F3 = 0x72, F4 = 0x73, F5 = 0x74, F6 = 0x75, F7 = 0x76, F8 = 0x77, F9 = 0x78, F10 = 0x89, F11 = 0x7A, F12 = 0x7B, F13 = 0x7C, F14 = 0x7D, F15 = 0x7E, F16 = 0x7F, F17 = 0x80, F18 = 0x81, F19 = 0x82, F20 = 0x83, F21 = 0x84, F22 = 0x85, F23 = 0x86, F24 = 0x87, NUMLOCK = 0x90, SCROLLLOCK = 0x91, COMMA = 0xBC, HIFFEN = 0xBD, DOT = 0xBE, BAR = 0xBF, SINGLEQUOTE = 0xD3}
  9285.     local numberkeys = {0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39}
  9286.  
  9287.     if type(key) == 'number' then
  9288.         if key == 0 then
  9289.             return 0x30
  9290.         end
  9291.         return numberkeys[key]
  9292.     end
  9293.     return keys[string.upper(key)]
  9294. end
  9295.  
  9296. function press(keys) -- Working
  9297.     local i = 1
  9298.     while i <= #keys do
  9299.         local key = ''
  9300.         if string.sub(keys, i, i) == '[' then
  9301.             i2 = i + string.find(string.sub(keys, i), ']')
  9302.             key = string.sub(keys, i+1, i2-2)
  9303.             keyevent(keyid(key))
  9304.             i = i2
  9305.         elseif string.sub(keys, i, i) ~= ']' then
  9306.             keyevent(keyid(string.sub(keys, i, i)))
  9307.             i = i + 1
  9308.         end
  9309.     end
  9310. end
  9311.  
  9312. function itemprice(itemname) -- Working
  9313.     return itemcost(itemname)
  9314. end
  9315.  
  9316. function filecontent(filename) -- Working
  9317.     if not fileexists(filename) then
  9318.         return ''
  9319.     end
  9320.     local handler = io.open(filename, 'r')
  9321.     content = handler:read('*a')
  9322.     handler:close()
  9323.     return content
  9324. end
  9325.  
  9326. function filelinescount(filename) -- Working
  9327.     if not fileexists(filename) then
  9328.         return 0
  9329.     end
  9330.     local linecount = 0
  9331.     for line in io.lines(filename) do
  9332.         linecount = linecount + 1
  9333.     end
  9334.     return linecount
  9335. end
  9336.  
  9337. function fileline(filename, linenum) -- Working
  9338.     local linen, linew = 0, ''
  9339.     for line in io.lines(filename) do
  9340.         linen = linen + 1
  9341.         if linen == linenum then
  9342.             linew = line
  9343.         end
  9344.     end
  9345.     return linew
  9346. end
  9347.  
  9348. function filewrite(filename, text) -- Working.
  9349.     local handler = io.open(filename, 'a+')
  9350.     handler:write(text)
  9351.     handler:close()
  9352. end
  9353.  
  9354. function fileexists(filename) -- Working
  9355.     local handler, exists = io.open(filename), false
  9356.     if type(handler) ~= 'nil' then
  9357.         exists = true
  9358.         handler:close()
  9359.     end
  9360.     local handler = nil
  9361.     return exists
  9362. end
  9363.  
  9364. function createfile(filename) -- Working
  9365.     if not fileexists(filename) then
  9366.         clearfile(filename)
  9367.     end
  9368. end
  9369.  
  9370. function execfile(filename)
  9371.     exec(filecontent(filename))
  9372. end
  9373.  
  9374. function filewriteline(filename, text) -- Working.
  9375.     local skip = ''
  9376.     if filelinescount(filename) > 0 then
  9377.         skip = '\n'
  9378.     end
  9379.     local handler = io.open(filename, 'a+')
  9380.     handler:write(skip..text)
  9381.     handler:close()
  9382. end
  9383.  
  9384. function clearfile(filename) -- Working.
  9385.     local handler = io.open(filename, 'w+')
  9386.     handler:close()
  9387. end
  9388.  
  9389. function filerewrite(filename, text)
  9390.     local handler = io.open(filename, 'w+')
  9391.     handler:write(text)
  9392.     handler:close()
  9393. end
  9394.  
  9395. function isfileline(filename, text) -- Working
  9396.     local n = 0
  9397.     if fileexists(filename) then
  9398.         for line in io.lines(filename) do
  9399.             n = n + 1
  9400.             if line == text then
  9401.                 return n
  9402.             end
  9403.         end
  9404.     end
  9405.     return false
  9406. end
  9407.  
  9408. function exec(execstring) -- Working
  9409.     local func = loadstring(execstring)
  9410.     func()
  9411. end
  9412.  
  9413. function vocation() -- Working
  9414.     local weapontype = findweapontype()
  9415.     if weapontype == 'rod' then
  9416.         return 'druid'
  9417.     elseif wapontype == 'wand' then
  9418.         return 'sorcerer'
  9419.     else
  9420.         local vocs = {'unknown', 5, 'mage', 10, 'paladin', 15, 'knight'}
  9421.         return vocs[(table.find(vocs, ($maxhp-185)/($level-8)) or 0)+1]
  9422.     end
  9423. end
  9424.  
  9425. function maxcap() -- Working
  9426.     local vocs = {'unknown', 0, 'druid', 10, 'sorcerer', 10, 'mage', 10, 'paladin', 20, 'knight', 30}
  9427.     return vocs[table.find(vocs, vocation())+1] * ($level - 8) + 470
  9428. end
  9429.  
  9430. function drawline(dir, length, x, y) -- Working. Needs inprovement
  9431.     local tab = {horizontal = {'_', 10, 0}, vertical = {'|', 0, 10}}
  9432.     local x, y, char, xi, yi = x or 0, y or 0, tab.dir[1], tab.dir[2], tab.dir[3]
  9433.     if not char or not length then
  9434.         return
  9435.     end
  9436.     for i = 1, length/10 do
  9437.         addtext(char, x + xi * i, y + yi * i)
  9438.     end
  9439. end
  9440.  
  9441. function string.explode(self, sep) -- By Socket, improved by Hardek. Working
  9442.     local result = {}
  9443.     self:gsub("[^".. sep .."*]+", function(s) table.insert(result, (string.gsub(s, "^%s*(.-)%s*$", "%1"))) end)
  9444.     return result
  9445. end
  9446.  
  9447. function sethealrule(rule, hprange, mprange, method, condition, spam) -- Working
  9448.     local settings = {'HealthRange', 'ManaRange', 'HealMethod', 'ExtraCondition', 'SpamRate'}
  9449.     local settingsTo = {((hprange:find('%%') and hprange:find(' %%')) and hprange:gsub('-', ' to ') or hprange:gsub('-', ' to '):gsub('%%', ' %%')):lower(), ((mprange:find('%%') and mprange:find(' %%')) and mprange:gsub('-', ' to ') or mprange:gsub('-', ' to '):gsub('%%', ' %%')):lower(), method:capitalizeall(), ((condition:lower():find('paralyze')) and 'If paralyzed' or ((condition == '') and 'No condition')):capitalize(), ((not spam) and '' or spam:gsub('-', ' to ')):lower()}
  9450.  
  9451.     for i = 1, #settings do
  9452.         setsetting('Healer/HealRules/'..rule..'/'..settings[i], settingsTo[i] or getsetting('Healer/HealRules/'..rule..'/'..settings[i]))
  9453.     end
  9454. end
  9455.  
  9456. function string.capitalize(self) -- Working
  9457.     return string.upper(self:sub(1,1)) .. self:sub(2):lower()
  9458. end
  9459.  
  9460. function string.capitalizeall(self) -- Working
  9461.     local t = string.explode(self, ' ')
  9462.     for i = 1, #t do
  9463.         t[i] = t[i]:capitalize()
  9464.     end
  9465.     return table.concat(t, ' ')
  9466. end
  9467.  
  9468. function bestskill() -- Working
  9469.     local t = {$axe+$axepc/100, {type = 'axe', skill = $axe, skillpc = $axepc}, $club+$clubpc/100, {type = 'club', skill = $club, skillpc = $clubpc}, $sword+$swordpc/100, {type = 'sword', skill = $sword, skillpc = $swordpc}, $distance+$distancepc/100, {type = 'distance', skill = $distance, skillpc = $distancepc}, $fist+$fistpc/100, {type = 'fist', skill = $fist, skillpc = $fistpc}}
  9470.     local j = 0
  9471.     for i = 1, #t, 2 do
  9472.         j = math.max(j, t[i])
  9473.     end
  9474.     return t[table.find2(t, j)+1]
  9475. end
  9476.  
  9477. function weaponskill() -- Working
  9478.     local t = {'axe', {type = 'axe', skill = $axe, skillpc = $axepc}, 'club', {type = 'club', skill = $club, skillpc = $clubpc}, 'sword', {type = 'sword', skill = $sword, skillpc = $swordpc}, {'bow', 'distance weapon'}, {type = 'distance', skill = $distance, skillpc = $distancepc}, 'no weapon', {type = 'fist', skill = $fist, skillpc = $fistpc}, {'rod', 'wand'}, {type = 'magic', skill = $mlevel, skillpc = $mlevelpc}}
  9479.     return t[table.find2(t, findweapontype())+1]
  9480. end
  9481.  
  9482. function table.find2(self, value, arg, notable, argonly) -- Working
  9483.     for i = 1, #self do
  9484.         if not argonly then
  9485.             if self[i] == value then
  9486.                 return i
  9487.             end
  9488.         end
  9489.         if type(self[i]) == 'table' then
  9490.             if arg then
  9491.                 if self[i][arg] == value then
  9492.                     return i
  9493.                 end
  9494.             elseif not notable then
  9495.                 for j = 1, #self[i] do
  9496.                     if self[i][j] == value then
  9497.                         return i, j
  9498.                     end
  9499.                 end
  9500.             end
  9501.         end
  9502.     end
  9503. end
  9504.  
  9505. function exptolvl(a, b) -- Working
  9506.     a = a or $level + 1
  9507.     if b then
  9508.         return exptolvl(b) - exptolvl(a)
  9509.     elseif a then
  9510.         return 50 / 3 * (a ^ 3 - 6 * a ^ 2 + 17 * a - 12)
  9511.     end
  9512. end
  9513.  
  9514. function levelpc() -- Working
  9515.     return math.floor(($exp - exptolvl($level)) * 100 / exptolvl($level, $level + 1))
  9516. end
  9517.  
  9518. function table.random(self, start, finish, count, step) -- Working
  9519.     self = {}
  9520.     step = step or 1
  9521.     count = (count ~= 0 and count) and count or math.floor((finish - start) / step)
  9522.     for i = 1, count do
  9523.         local r = math.random(start, finish)
  9524.         while table.find(self, r) do
  9525.             r = math.random(start, finish)
  9526.         end
  9527.         table.insert(self, r)
  9528.     end
  9529.     return self
  9530. end
  9531.  
  9532. function iscursorin(sx, sy, fx, fy, area) -- working
  9533.     if area then
  9534.         fx, fy = sx + fx, sy + fy
  9535.     end
  9536.     if $cursor.x >= sx then
  9537.         if $cursor.x <= fx then
  9538.             if $cursor.y >= sy then
  9539.                 if $cursor.y <= fy then
  9540.                     return true
  9541.                 end
  9542.             end
  9543.         end
  9544.     end
  9545.     return false
  9546. end
  9547.  
  9548. function utcoffset() -- Working
  9549.     local now = os.time()
  9550.     return os.difftime(now, os.time(os.date("!*t", now)) - (os.date('*t').isdst and 3600 or 0))
  9551. end
  9552.  
  9553. function cetoffset() -- Probably working
  9554.     local now = os.time()
  9555.     return os.difftime(now, os.time(os.date("!*t", now)) + 3600)
  9556. end
  9557.  
  9558.  
  9559. function utctime() -- Working
  9560.     return tosec(os.date('%X')) - utcoffset()
  9561. end
  9562.  
  9563.  
  9564. function cettime() -- Probably working
  9565.     return tosec(os.date('%X')) - cetoffset()
  9566. end
  9567.  
  9568. function timezone() -- Working
  9569.     if utcoffset() then
  9570.         return 'UTC '..utcoffset()/3600
  9571.     end
  9572.     return 'UTC'
  9573. end
  9574.  
  9575. function sstime(world) -- Probably working
  9576.     world = world:lower()
  9577.     local ssworlds = {
  9578.         8, {'arcania', 'askara', 'aurea', 'berylia', 'celesta', 'furora', 'galana', 'guardia', 'iridia', 'kyra', 'morgana', 'nebula', 'obsidia', 'pandoria', 'refugia', 'saphira', 'selena', 'thoria', 'xerena'},
  9579.         9, {'aldora', 'antica', 'azuera', 'candia', 'danubia', 'elysia', 'eternia', 'harmonia', 'hiberna', 'inferna', 'isara', 'lunara', 'nerana', 'nova', 'premia', 'secura', 'titania', 'valoria'},
  9580.         11, {'astera', 'balera', 'danera', 'elera', 'empera', 'fortera', 'grimera', 'honera', 'jamera', 'keltera', 'lucera', 'luminera', 'malvera', 'menera', 'neptera', 'ocera', 'pythera', 'samera', 'shanera', 'shivera', 'silvera', 'tenebra', 'vinera', 'zanera'},
  9581.         12, {'amera', 'calmera', 'chimera', 'dolera', 'julera', 'libera', 'mythera', 'pacera', 'rubera', 'solera', 'trimera', 'unitera', 'xantera'}
  9582.                         }
  9583.     for i = 2, 8, 2 do
  9584.         if table.binaryfind(ssworlds[i], world) then
  9585.             return (ssworlds[i-1] * 3600 - cettime()) % 86400
  9586.         end
  9587.     end
  9588. end
  9589.  
  9590. function time(secs, pattern) -- Working
  9591.     local times = {dd = math.floor(secs / 86400), hh = math.floor(secs / 3600) % 24, mm = math.floor(secs / 60) % 60, ss = secs % 60}
  9592.     if not pattern then
  9593.         if times.dd > 0 then
  9594.             pattern = 'dd:hh:mm:ss'
  9595.         elseif times.hh > 0 then
  9596.             pattern = 'hh:mm:ss'
  9597.         else
  9598.             pattern = 'mm:ss'
  9599.         end
  9600.     end
  9601.     pattern = pattern:lower()
  9602.     for k, v in pairs(times) do
  9603.         pattern = string.gsub(pattern, k, math.format(v, "00"))
  9604.     end
  9605.     return pattern
  9606. end
  9607.  
  9608. function math.format(self, pattern) -- Working
  9609.     local a, b = pattern, tostring(self)
  9610.     local c, d = (a:find("%.")), (b:find("%."))
  9611.     local za, zb = math.max(0, (c or #a + 1) - (d or #b + 1)), math.max(0, (#a - (c or 99999)) - (#b - (d or #b)))
  9612.     local dot = (c and not d) and '.' or ''
  9613.     return string.rep("0", za) .. b .. dot .. string.rep("0", zb)
  9614. end
Advertisement
Add Comment
Please, Sign In to add comment