diff --git a/CHANGELOG b/CHANGELOG index aac28e4f8..29ad8c1d5 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -73,6 +73,10 @@ - Added advance reward system this are disable only on 10.x - Only here are supported in the moment - Added attributes functions from 0.3.7 only on 10.x - Only here are supported in the moment - Added exhausted block on talkactions .. this option worn on onsay and onuse this cool only on 10.x - Only here are supported in the moment + - Added functions from 0.3.7: only on 10.x - Only here are supported in the moment + getMonster - getHouseByPlayerGUID - getPlayersByAccountNumber - getPlayersByIPAddress - setDescription - setText - setUniqueId - isPromoted - is(isDruid, isKnight, isPaladin, isMage, isSorcerer) + depositMoney - transferMoneyTo - withdrawMoney - getTile - string.split - string.trim - string.starts - string.titleCase - isHouse - isPz + tables - Always reload global.lua libraries - Fix bug with /town command - Fix to: http://www.blacktibia.org/t40273-otx-server-3-2-phantom-8-6-8-70-72-10-90#245403/ diff --git a/path_10_9/data/actions/scripts/other/enchanting.lua b/path_10_9/data/actions/scripts/other/enchanting.lua index 0b7e808fb..23b2e76a9 100644 --- a/path_10_9/data/actions/scripts/other/enchanting.lua +++ b/path_10_9/data/actions/scripts/other/enchanting.lua @@ -42,20 +42,6 @@ local enchantedItems = { } function onUse(player, item, fromPosition, target, toPosition, isHotkey) - if isInArray({33268, 33269}, toPosition.x) and toPosition.y == 31830 and toPosition.z == 10 and player:getStorageValue(Storage.ElementalSphere.QuestLine) > 0 then - if not isInArray(spheres[item.itemid], player:getVocation():getId()) then - return false - elseif isInArray({7915, 7916}, target.itemid) then - player:say('Turn off the machine first.', TALKTYPE_MONSTER_SAY) - return true - else - player:setStorageValue(Storage.ElementalSphere.MachineGemCount, math.max(1, player:getStorageValue(Storage.ElementalSphere.MachineGemCount) + 1)) - toPosition:sendMagicEffect(CONST_ME_PURPLEENERGY) - item:transform(item.itemid, item.type - 1) - return true - end - end - if item.itemid == 2147 and target.itemid == 2342 then target:transform(2343) target:decay() diff --git a/path_10_9/data/lib/core/core.lua b/path_10_9/data/lib/core/core.lua index 1b78513f1..96d770751 100644 --- a/path_10_9/data/lib/core/core.lua +++ b/path_10_9/data/lib/core/core.lua @@ -6,5 +6,8 @@ dofile('data/lib/core/item.lua') dofile('data/lib/core/itemtype.lua') dofile('data/lib/core/player.lua') dofile('data/lib/core/position.lua') +dofile('data/lib/core/string.lua') +dofile('data/lib/core/tables.lua') dofile('data/lib/core/teleport.lua') dofile('data/lib/core/tile.lua') +dofile('data/lib/core/vocation.lua') diff --git a/path_10_9/data/lib/core/creature.lua b/path_10_9/data/lib/core/creature.lua index e0fd78578..9a7c7dd08 100644 --- a/path_10_9/data/lib/core/creature.lua +++ b/path_10_9/data/lib/core/creature.lua @@ -27,6 +27,10 @@ function Creature.getClosestFreePosition(self, position, extended) return Position() end +function Creature.getMonster(self) + return self:isMonster() and self or nil +end + function Creature.getPlayer(self) return self:isPlayer() and self or nil end diff --git a/path_10_9/data/lib/core/game.lua b/path_10_9/data/lib/core/game.lua index 4e0c5d8aa..673c5c34d 100644 --- a/path_10_9/data/lib/core/game.lua +++ b/path_10_9/data/lib/core/game.lua @@ -40,6 +40,43 @@ function Game.getReverseDirection(direction) return NORTH end +function Game.getHouseByPlayerGUID(playerGUID) + local houses, house = Game.getHouses() + for i = 1, #houses do + house = houses[i] + if house:getOwnerGuid() == playerGUID then + return house + end + end + return nil +end + +function Game.getPlayersByAccountNumber(accountNumber) + local result = {} + local players, player = Game.getPlayers() + for i = 1, #players do + player = players[i] + if player:getAccountId() == accountNumber then + result[#result + 1] = player + end + end + return result +end + +function Game.getPlayersByIPAddress(ip, mask) + if not mask then mask = 0xFFFFFFFF end + local masked = bit.band(ip, mask) + local result = {} + local players, player = Game.getPlayers() + for i = 1, #players do + player = players[i] + if bit.band(player:getIp(), mask) == masked then + result[#result + 1] = player + end + end + return result +end + function Game.getSkillType(weaponType) if weaponType == WEAPON_CLUB then return SKILL_CLUB @@ -60,7 +97,7 @@ if not globalStorageTable then end function Game.getStorageValue(key) - return globalStorageTable[key] + return globalStorageTable[key] or -1 end function Game.setStorageValue(key, value) diff --git a/path_10_9/data/lib/core/item.lua b/path_10_9/data/lib/core/item.lua index 7980d5ae1..fc699bf93 100644 --- a/path_10_9/data/lib/core/item.lua +++ b/path_10_9/data/lib/core/item.lua @@ -21,3 +21,27 @@ end function Item.isTile(self) return false end + +function Item.setDescription(self, description) + if description ~= '' then + self:setAttribute(ITEM_ATTRIBUTE_DESCRIPTION, description) + else + self:removeAttribute(ITEM_ATTRIBUTE_DESCRIPTION) + end +end + +function Item.setText(self, text) + if text ~= '' then + self:setAttribute(ITEM_ATTRIBUTE_TEXT, text) + else + self:removeAttribute(ITEM_ATTRIBUTE_TEXT) + end +end + +function Item.setUniqueId(self, uniqueId) + if type(uniqueId) ~= 'number' or uniqueId < 0 or uniqueId > 65535 then + return false + end + + self:setAttribute(ITEM_ATTRIBUTE_UNIQUEID, uniqueId) +end diff --git a/path_10_9/data/lib/core/player.lua b/path_10_9/data/lib/core/player.lua index 8fae5bd63..26d2f0b7c 100644 --- a/path_10_9/data/lib/core/player.lua +++ b/path_10_9/data/lib/core/player.lua @@ -21,6 +21,16 @@ function Player.feed(self, food) return true end +function Player.getBlessings(self) + local blessings = 0 + for i = 1, 5 do + if self:hasBlessing(i) then + blessings = blessings + 1 + end + end + return blessings +end + function Player.getClosestFreePosition(self, position, extended) if self:getAccountType() >= ACCOUNT_TYPE_GOD then return position @@ -33,7 +43,6 @@ function Player.getDepotItems(self, depotId) end function Player.getLossPercent(self) - local blessings = 0 local lossPercent = { [0] = 100, [1] = 70, @@ -43,18 +52,41 @@ function Player.getLossPercent(self) [5] = 0 } - for i = 1, 5 do - if self:hasBlessing(i) then - blessings = blessings + 1 - end - end - return lossPercent[blessings] + return lossPercent[self:getBlessings()] +end + +function Player.isDruid(self) + return isInArray({2, 6}, self:getVocation():getId()) +end + +function Player.isKnight(self) + return isInArray({4, 8}, self:getVocation():getId()) +end + +function Player.isPaladin(self) + return isInArray({3, 7}, self:getVocation():getId()) +end + +function Player.isMage(self) + return isInArray({1, 2, 5, 6}, self:getVocation():getId()) +end + +function Player.isSorcerer(self) + return isInArray({1, 5}, self:getVocation():getId()) end function Player.isPremium(self) return self:getPremiumDays() > 0 or configManager.getBoolean(configKeys.FREE_PREMIUM) end +function Player.isPromoted(self) + local vocation = self:getVocation() + local promotedVocation = vocation:getPromotion() + promotedVocation = promotedVocation and promotedVocation:getId() or 0 + + return promotedVocation == 0 and vocation:getId() ~= promotedVocation +end + function Player.sendCancelMessage(self, message) if type(message) == "number" then message = Game.getReturnMessage(message) @@ -96,3 +128,42 @@ function Player.addManaSpent(...) APPLY_SKILL_MULTIPLIER = true return ret end + +function Player.depositMoney(self, amount) + if not self:removeMoney(amount) then + return false + end + + self:setBankBalance(self:getBankBalance() + amount) + return true +end + +function Player.transferMoneyTo(self, target, amount) + local balance = self:getBankBalance() + if amount > balance then + return false + end + + local targetPlayer = Player(target) + if targetPlayer then + targetPlayer:setBankBalance(targetPlayer:getBankBalance() + amount) + else + if not playerExists(target) then + return false + end + db.query("UPDATE `players` SET `balance` = `balance` + '" .. amount .. "' WHERE `name` = " .. db.escapeString(target)) + end + + self:setBankBalance(self:getBankBalance() - amount) + return true +end + +function Player.withdrawMoney(self, amount) + local balance = self:getBankBalance() + if amount > balance or not self:addMoney(amount) then + return false + end + + self:setBankBalance(balance - amount) + return true +end diff --git a/path_10_9/data/lib/core/position.lua b/path_10_9/data/lib/core/position.lua index 572c6a29f..6875a7683 100644 --- a/path_10_9/data/lib/core/position.lua +++ b/path_10_9/data/lib/core/position.lua @@ -18,6 +18,10 @@ function Position:getNextPosition(direction, steps) end end +function Position.getTile(self) + return Tile(self) +end + function Position:moveUpstairs() local isWalkable = function (position) local tile = Tile(position) diff --git a/path_10_9/data/lib/core/string.lua b/path_10_9/data/lib/core/string.lua new file mode 100644 index 000000000..63f275378 --- /dev/null +++ b/path_10_9/data/lib/core/string.lua @@ -0,0 +1,19 @@ +string.split = function(str, sep) + local res = {} + for v in str:gmatch("([^" .. sep .. "]+)") do + res[#res + 1] = v + end + return res +end + +string.trim = function(str) + return str:match'^()%s*$' and '' or str:match'^%s*(.*%S)' +end + +string.starts = function(str, substr) + return string.sub(str, 1, #substr) == substr +end + +string.titleCase = function(str) + return str:gsub("(%a)([%w_']*)", function(first, rest) return first:upper() .. rest:lower() end) +end diff --git a/path_10_9/data/lib/core/tables.lua b/path_10_9/data/lib/core/tables.lua new file mode 100644 index 000000000..a2d225c56 --- /dev/null +++ b/path_10_9/data/lib/core/tables.lua @@ -0,0 +1,105 @@ +table.append = table.insert +table.empty = function (t) + return next(t) == nil +end + +table.find = function (table, value) + for i, v in pairs(table) do + if(v == value) then + return i + end + end + + return nil +end + +table.contains = function (txt, str) + for i, v in pairs(str) do + if(txt:find(v) and not txt:find('(%w+)' .. v) and not txt:find(v .. '(%w+)')) then + return true + end + end + + return false +end +table.isStrIn = table.contains + +table.count = function (table, item) + local count = 0 + for i, n in pairs(table) do + if(item == n) then + count = count + 1 + end + end + + return count +end +table.countElements = table.count + +table.getCombinations = function (table, num) + local a, number, select, newlist = {}, #table, num, {} + for i = 1, select do + a[#a + 1] = i + end + + local newthing = {} + while(true) do + local newrow = {} + for i = 1, select do + newrow[#newrow + 1] = table[a[i]] + end + + newlist[#newlist + 1] = newrow + i = select + while(a[i] == (number - select + i)) do + i = i - 1 + end + + if(i < 1) then + break + end + + a[i] = a[i] + 1 + for j = i, select do + a[j] = a[i] + j - i + end + end + + return newlist +end + +function table.serialize(x, recur) + local t = type(x) + recur = recur or {} + + if(t == nil) then + return "nil" + elseif(t == "string") then + return string.format("%q", x) + elseif(t == "number") then + return tostring(x) + elseif(t == "boolean") then + return t and "true" or "false" + elseif(getmetatable(x)) then + error("Can not serialize a table that has a metatable associated with it.") + elseif(t == "table") then + if(table.find(recur, x)) then + error("Can not serialize recursive tables.") + end + table.append(recur, x) + + local s = "{" + for k, v in pairs(x) do + s = s .. "[" .. table.serialize(k, recur) .. "]" + s = s .. " = " .. table.serialize(v, recur) .. "," + end + s = s .. "}" + return s + else + error("Can not serialize value of type '" .. t .. "'.") + end +end + +function table.unserialize(str) + return loadstring("return " .. str)() +end \ No newline at end of file diff --git a/path_10_9/data/lib/core/tile.lua b/path_10_9/data/lib/core/tile.lua index e2e26c4ba..b7099c784 100644 --- a/path_10_9/data/lib/core/tile.lua +++ b/path_10_9/data/lib/core/tile.lua @@ -2,10 +2,19 @@ function Tile.isCreature(self) return false end +function Tile.isHouse(self) + local house = self:getHouse() + return not not house +end + function Tile.isItem(self) return false end +function Tile.isPz(self) + return self:hasFlag(TILESTATE_PROTECTIONZONE) +end + function Tile.isTile(self) return true end diff --git a/path_10_9/data/lib/core/vocation.lua b/path_10_9/data/lib/core/vocation.lua new file mode 100644 index 000000000..fbaffda1e --- /dev/null +++ b/path_10_9/data/lib/core/vocation.lua @@ -0,0 +1,11 @@ +function Vocation.getBase(self) + local demotion = self:getDemotion() + while demotion do + local tmp = demotion:getDemotion() + if not tmp then + return demotion + end + demotion = tmp + end + return self +end