From 81826f14b9896c9c3aa1411903d58187d2e71ee5 Mon Sep 17 00:00:00 2001 From: Eduardo Dantas Date: Sun, 7 Jun 2020 01:59:13 -0300 Subject: [PATCH] Feat: adding custom map (containing training room and npcs shop) (#1299) * Feat: adding custom maps * Fixed Mazarius position * Add missing npc Zurak Custom area (event room) added, with trainers, npcs shop and respective loading scripts Npc/map/attribute loading functions have been moved to 051-functions Removed npcs shop area from global map and moved to custom map Custom area npcs are created by entering the teleport that leads to the event room (located in thais temple) For disable the custom map, is only set in "data/lib/tables/additional_map.lua" to "enabled = false" All map attribute loading scripts (be it npc/action/unique/item/map) have been moved to startup.lua The custom map is in the folder world/custom/otservbr-custom.otbm The custom scripts in the folder data/scripts/custom (without type separation, action/movement/monster etc) --- data/globalevents/scripts/others/startup.lua | 24 +-- data/lib/core/storages.lua | 2 + data/lib/miscellaneous/050-functions.lua | 122 ++++++++++++ data/lib/tables/action_unique.lua | 12 +- data/lib/tables/additional_map.lua | 4 +- data/lib/tables/npc_spawn_list.lua | 79 +++++--- data/npc/cassino.xml | 5 + data/npc/scripts/custom/cassino.lua | 176 ++++++++++++++++++ .../custom/monster_training_machine.lua | 96 ++++++++++ data/scripts/custom/movement_npcs_create.lua | 22 +++ .../custom/movement_trainer_entrance.lua | 76 ++++++++ data/scripts/custom/movement_trainer_exit.lua | 30 +++ data/scripts/globalevents/load_attributes.lua | 108 ----------- data/scripts/globalevents/npcs_spawn.lua | 17 -- data/world/custom/otservbr-custom-houses.xml | 5 + data/world/custom/otservbr-custom-spawn.xml | 2 + data/world/otservbr-spawn.xml | 13 -- 17 files changed, 608 insertions(+), 185 deletions(-) create mode 100644 data/npc/cassino.xml create mode 100644 data/npc/scripts/custom/cassino.lua create mode 100644 data/scripts/custom/monster_training_machine.lua create mode 100644 data/scripts/custom/movement_npcs_create.lua create mode 100644 data/scripts/custom/movement_trainer_entrance.lua create mode 100644 data/scripts/custom/movement_trainer_exit.lua delete mode 100644 data/scripts/globalevents/load_attributes.lua delete mode 100644 data/scripts/globalevents/npcs_spawn.lua create mode 100644 data/world/custom/otservbr-custom-houses.xml create mode 100644 data/world/custom/otservbr-custom-spawn.xml diff --git a/data/globalevents/scripts/others/startup.lua b/data/globalevents/scripts/others/startup.lua index 5847c4fab..571609bb3 100644 --- a/data/globalevents/scripts/others/startup.lua +++ b/data/globalevents/scripts/others/startup.lua @@ -1,7 +1,3 @@ -local additionalMap = { - { description = "map description", file = "data/world/worldchanges/example.otbm", enabled = false} -} - local startupGlobalStorages = { GlobalStorage.TheAncientTombs.AshmunrahSwitchesGlobalStorage, GlobalStorage.TheAncientTombs.DiprathSwitchesGlobalStorage, @@ -35,19 +31,17 @@ local startupGlobalStorages = { } function onStartup() - print(">> Loading additional maps") - for index, value in ipairs(AdditionalMap) do - if value.enabled then - Game.loadMap(value.file) - print("> Loaded " .. (#AdditionalMap) .. " additional map.") - end - end + loadCustomMaps() + print("> Loaded " .. (#CustomMapTable) .. " custom map.") - print(string.format(">> Loaded ".. (#NpcTable) .." npcs and spawned %d monsters.\n>> \z + loadLuaNpcs() + print(string.format("> Loaded ".. (#NpcTable) .." npcs and spawned %d monsters.\n> \z Loaded %d towns with %d houses in total.", Game.getMonsterCount(), #Game.getTowns(), #Game.getHouses())) - print(">> Loaded " .. (#SignTable) .. " signs in the map.") - print(">> Loaded " .. (#BookTable) .. " books in the map.") - print(">> Loaded action and unique per Lua") + + loadLuaMapAttributes() + print("> Loaded " .. (#SignTable) .. " signs in the map.") + print("> Loaded " .. (#BookTable) .. " books in the map.") + print("> Loaded action and unique per Lua") for i = 1, #startupGlobalStorages do Game.setStorageValue(startupGlobalStorages[i], 0) diff --git a/data/lib/core/storages.lua b/data/lib/core/storages.lua index 18f06c5d7..3a2f19f7f 100644 --- a/data/lib/core/storages.lua +++ b/data/lib/core/storages.lua @@ -1791,6 +1791,8 @@ Storage = { Factions = 50723, blockMovementStorage = 100000, PetSummon = 60045, + TrainerRoom = 60046, + NpcSpawn = 60047, isTraining = 37 } diff --git a/data/lib/miscellaneous/050-functions.lua b/data/lib/miscellaneous/050-functions.lua index 42a6608e4..82cdacae5 100644 --- a/data/lib/miscellaneous/050-functions.lua +++ b/data/lib/miscellaneous/050-functions.lua @@ -500,3 +500,125 @@ function checkWeightAndBackpackRoom(player, itemWeight, message) end return true end + +function loadLuaMapAttributes() + print(">> Loading map attributes.") + -- It load actions + for index, value in pairs(ActionTable) do + for i = 1, #value.itemPos do + local tile = Tile(value.itemPos[i]) + local item + -- Checks if the position is valid + if tile then + -- Checks that you have no items created + if tile:getItemCountById(value.itemId) == 0 then + -- If not have items created, this create the item + item = Game.createItem(value.itemId, 1, value.itemPos[i]) + end + if not item then + item = tile:getItemById(value.itemId) + end + -- If he found the item, add the action id. + if item and value.actionId then + item:setActionId(value.actionId) + end + if value.itemId == false and tile:getTopDownItem() then + tile:getTopDownItem():setActionId(value.actionId) + end + if value.itemId == false and tile:getTopTopItem() then + tile:getTopTopItem():setActionId(value.actionId) + end + -- This function add one action id on an item inside the container + -- It was developed to add action on daily respawn item + if item and value.isDailyAIDContainerItem then + itemAttr = item:addItem(value.containerItem, 1) + itemAttr:setActionId(value.actionId) + end + end + end + end + -- It load uniques + for key, value in pairs(UniqueTable) do + local tile = Tile(value.itemPos) + local item + -- Checks if the position is valid + if tile then + -- Checks that you have no items created + if tile:getItemCountById(value.itemId) == 0 then + -- If not have items created, thisc create the item + item = Game.createItem(value.itemId, 1, value.itemPos) + end + if not item then + item = tile:getItemById(value.itemId) + end + -- If he found the item, add the unique id + if item then + item:setAttribute(ITEM_ATTRIBUTE_UNIQUEID, key) + end + end + end + -- It load signs on map table + for key, value in pairs(SignTable) do + local tile = Tile(value.itemPos) + local item + -- Checks if the position is valid + if tile then + -- Checks that you have no items created + if tile:getItemCountById(value.itemId) == 0 then + -- Create item + item = Game.createItem(value.itemId, 1, value.itemPos) + end + if not item then + item = tile:getItemById(value.itemId) + end + -- If he found the item, add the text + if item then + item:setAttribute(ITEM_ATTRIBUTE_DESCRIPTION, value.text) + end + end + end + -- It load book on map table + for key, value in pairs(BookTable) do + local tile = Tile(value.itemPos) + local item + -- Checks if the position is valid + if tile then + -- Checks that you have no items created + if tile:getItemCountById(value.itemId) == 0 then + -- Create item + item = Game.createItem(value.itemId, 1, value.itemPos) + end + if not item then + item = tile:getItemById(value.itemId) + end + -- If he found the item, add the text + if item then + item:setAttribute(ITEM_ATTRIBUTE_TEXT, value.text) + end + end + end +end + +function loadLuaNpcs() + print(">> Loading NPC's, monsters and houses.") + for i = 1,#NpcTable do + local npc = NpcTable[i] + if npc and npc.name and npc.position then + local spawn = Game.createNpc(npc.name, npc.position) + if spawn then + spawn:setMasterPos(npc.position) + end + end + end +end + +function loadCustomMaps() + print(">> Loading custom maps.") + for index, value in ipairs(CustomMapTable) do + if value.enabled then + -- It's load the map + Game.loadMap(value.file) + Game.setStorageValue(Storage.NpcSpawn, -1) + end + end +end diff --git a/data/lib/tables/action_unique.lua b/data/lib/tables/action_unique.lua index 109158ff1..64b4f90ae 100644 --- a/data/lib/tables/action_unique.lua +++ b/data/lib/tables/action_unique.lua @@ -1085,10 +1085,20 @@ UniqueTable = { }, [25030] = { itemId = 3706, - itemPos = Position(33277, 31754, 7), + itemPos = {x = 33277, y = 31754, z = 7}, storage = Storage.TibiaTales.JackFutureQuest.Statue, value = 1, setStorage = Storage.TibiaTales.JackFutureQuest.QuestLine, addItem = 11343 + }, + -- Custom trainer entrance + [25031] = { + itemId = 8058, + itemPos = {x = 1116, y = 1092, z = 7} + }, + -- Custom npcs create + [25032] = { + itemId = false, + itemPos = {x = 32373, y = 32236, z = 7} } } diff --git a/data/lib/tables/additional_map.lua b/data/lib/tables/additional_map.lua index 4bc8dfb53..2a2d104cb 100644 --- a/data/lib/tables/additional_map.lua +++ b/data/lib/tables/additional_map.lua @@ -1,3 +1,3 @@ -AdditionalMap = { - [1] = {file = "data/world/additional/example.otbm", enabled = false} +CustomMapTable = { + [1] = {file = "data/world/custom/otservbr-custom.otbm", enabled = true} } diff --git a/data/lib/tables/npc_spawn_list.lua b/data/lib/tables/npc_spawn_list.lua index edf421d05..17bb6aaca 100644 --- a/data/lib/tables/npc_spawn_list.lua +++ b/data/lib/tables/npc_spawn_list.lua @@ -116,7 +116,7 @@ NpcTable = { [115] = {name = "ormuhn", position = {x = 33159, y = 32810, z = 5}}, [116] = {name = "mehkesh", position = {x = 33130, y = 32811, z = 5}}, [117] = {name = "fenech", position = {x = 33131, y = 32820, z = 5}}, - [118] = {name = "tamoril", position = {x = 31908, y = 33100, z = 5}}, + [118] = {name = "tamed_lion", position = {x = 33874, y = 31487, z = 4}}, [119] = {name = "tereban", position = {x = 10191, y = 10085, z = 6}}, [120] = {name = "frosty", position = {x = 33888, y = 31016, z = 6}}, [121] = {name = "siflind", position = {x = 32360, y = 31030, z = 6}}, @@ -281,12 +281,12 @@ NpcTable = { [280] = {name = "jack_fate", position = {x = 32286, y = 32891, z = 6}}, [281] = {name = "guide_davina", position = {x = 32275, y = 32894, z = 6}}, [282] = {name = "captain_max", position = {x = 32298, y = 32895, z = 6}}, - [283] = {name = "hanna", position = {x = 31885, y = 33060, z = 6}}, - [284] = {name = "yasir", position = {x = 31867, y = 33068, z = 6}}, - [285] = {name = "lailene", position = {x = 31896, y = 33077, z = 6}}, - [286] = {name = "alexander", position = {x = 31862, y = 33084, z = 6}}, - [287] = {name = "esrik", position = {x = 31890, y = 33099, z = 6}}, - [288] = {name = "rock_in_a_hard_place", position = {x = 31860, y = 33105, z = 6}}, + [283] = {name = "saideh", position = {x = 33844, y = 31638, z = 7}}, + [284] = {name = "tarun", position = {x = 32976, y = 32715, z = 7}}, + [285] = {name = "nomadnpc", position = {x = 31941, y = 31305, z = 6}}, + [286] = {name = "kais", position = {x = 32910, y = 32512, z = 8}}, + [287] = {name = "pythius_the_rottennpc", position = {x = 32590,y = 31407,z = 15}}, + [288] = {name = "iwar", position = {x = 32618,y = 31917,z = 8}}, [289] = {name = "sane_mage", position = {x = 10320, y = 10089, z = 7}}, [290] = {name = "asima", position = {x = 12067, y = 12012, z = 7}}, [291] = {name = "mugluf", position = {x = 12067, y = 12025, z = 7}}, @@ -344,7 +344,7 @@ NpcTable = { [343] = {name = "buddel_tyrsung", position = {x = 32332, y = 31227, z = 7}}, [344] = {name = "oliver", position = {x = 32894, y = 31228, z = 7}}, [345] = {name = "zurak", position = {x = 33154, y = 31230, z = 7}}, - [346] = {name = "orc_berserker_npc", position = {x = 32777, y = 31237, z = 7}}, + [346] = {name = "zurak", position = {x = 33158, y = 31225, z = 7}}, [347] = {name = "dorbin", position = {x = 32783, y = 31236, z = 7}}, [348] = {name = "oiriz", position = {x = 32787, y = 31238, z = 7}}, [349] = {name = "a_grumpy_cyclops", position = {x = 32822, y = 31238, z = 7}}, @@ -665,13 +665,13 @@ NpcTable = { [664] = {name = "jason", position = {x = 32157, y = 32939, z = 7}}, [665] = {name = "danlon", position = {x = 32190, y = 32949, z = 7}}, [666] = {name = "meraya", position = {x = 32194, y = 32974, z = 7}}, - [667] = {name = "alesar", position = {x = 31856, y = 33056, z = 7}}, - [668] = {name = "yaman", position = {x = 31887, y = 33058, z = 7}}, - [669] = {name = "nah_bob", position = {x = 31860, y = 33085, z = 7}}, - [670] = {name = "guide_kroak", position = {x = 31882, y = 33084, z = 7}}, - [671] = {name = "rashid", position = {x = 31887, y = 33101, z = 7}}, - [672] = {name = "haroun", position = {x = 31859, y = 33105, z = 7}}, - [673] = {name = "mazarius", position = {x = 12124, y = 11999, z = 8}}, + [667] = {name = "tanyt", position = {x = 33957, y = 31513, z = 0}}, + [668] = {name = "the_empress", position = {x = 33868, y = 31497, z = 3}}, + [669] = {name = "the_librarian", position = {x = 33873, y = 31494, z = 5}}, + [670] = {name = "yonan", position = {x = 33922, y = 31513, z = 7}}, + [671] = {name = "shimun", position = {x = 33758, y = 31494, z = 7}}, + [672] = {name = "tefrit", position = {x = 33839, y = 31693, z = 5}}, + [673] = {name = "noozer", position = {x = 32502, y = 32338, z = 8}}, [674] = {name = "rebel", position = {x = 33198, y = 31060, z = 8}}, [675] = {name = "lizard_tunnel_guard", position = {x = 33385, y = 31068, z = 8}}, [676] = {name = "lizard_tunnel_guard", position = {x = 33387, y = 31076, z = 8}}, @@ -725,7 +725,7 @@ NpcTable = { [724] = {name = "victor", position = {x = 32255, y = 32216, z = 8}}, [725] = {name = "henricus", position = {x = 32316, y = 32267, z = 8}}, [726] = {name = "partos", position = {x = 32323, y = 32280, z = 8}}, - [727] = {name = "noozer", position = {x = 32502, y = 32338, z = 8}}, + [727] = {name = "mazarius", position = {x = 33277, y = 32390, z = 8}}, [728] = {name = "mazarius", position = {x = 33277, y = 32390, z = 8}}, [729] = {name = "jamesfrancis", position = {x = 31939, y = 32502, z = 8}}, [730] = {name = "gnommander", position = {x = 32248, y = 32604, z = 8}}, @@ -951,17 +951,38 @@ NpcTable = { [950] = {name = "ninev", position = {x = 33871, y = 31528, z = 7}}, [951] = {name = "ninos", position = {x = 33904, y = 31498, z = 7}}, [952] = {name = "ramina", position = {x = 33903, y = 31495, z = 7}}, - [953] = {name = "tamed_lion", position = {x = 33874, y = 31487, z = 4}}, - [954] = {name = "tanyt", position = {x = 33957, y = 31513, z = 0}}, - [955] = {name = "the_empress", position = {x = 33868, y = 31497, z = 3}}, - [956] = {name = "the_librarian", position = {x = 33873, y = 31494, z = 5}}, - [957] = {name = "yonan", position = {x = 33922, y = 31513, z = 7}}, - [958] = {name = "shimun", position = {x = 33758, y = 31494, z = 7}}, - [959] = {name = "tefrit", position = {x = 33839, y = 31693, z = 5}}, - [960] = {name = "saideh", position = {x = 33844, y = 31638, z = 7}}, - [961] = {name = "tarun", position = {x = 32976, y = 32715, z = 7}}, - [962] = {name = "nomadnpc", position = {x = 31941, y = 31305, z = 6}}, - [963] = {name = "kais", position = {x = 32910, y = 32512, z = 8}}, - [964] = {name = "pythius_the_rottennpc", position = {x = 32590,y = 31407,z = 15}}, - [965] = {name = "iwar", position = {x = 32618,y = 31917,z = 8}} + [953] = {name = "orc_berserker_npc", position = {x = 32777, y = 31237, z = 7}} +} + +CustomNpcTable = { + --Custom map (event room) + --Trade island + [1] = {name = "alesar", position = {x = 953, y = 948, z = 7}}, + [2] = {name = "yaman", position = {x = 983, y = 951, z = 7}}, + [3] = {name = "nah_bob", position = {x = 956, y = 977, z = 7}}, + [4] = {name = "guide_kroak", position = {x = 976, y = 977, z = 7}}, + [5] = {name = "rashid", position = {x = 984, y = 994, z = 7}}, + [6] = {name = "haroun", position = {x = 956, y = 998, z = 7}}, + [7] = {name = "hanna", position = {x = 983, y = 951, z = 6}}, + [8] = {name = "yasir", position = {x = 963, y = 959, z = 6}}, + [9] = {name = "lailene", position = {x = 991, y = 969, z = 6}}, + [10] = {name = "alexander", position = {x = 957, y = 976, z = 6}}, + [11] = {name = "esrik", position = {x = 985, y = 991, z = 6}}, + [12] = {name = "rock_in_a_hard_place", position = {x = 956, y = 997, z = 6}}, + [13] = {name = "tamoril", position = {x = 1002, y = 992, z = 5}}, + --NPC beach + [14] = {name = "zuma_magehide", position = {x = 1058, y = 1020, z = 7}}, + [15] = {name = "runtel_blackspark", position = {x = 1067, y = 1020, z = 7}}, + [16] = {name = "rock_in_a_hard_place", position = {x = 993, y = 1034, z = 7}}, + [17] = {name = "archery", position = {x = 990, y = 1027, z = 7}}, + [18] = {name = "hanna", position = {x = 1003, y = 1019, z = 7}}, + [19] = {name = "yasir", position = {x = 984, y = 1029, z = 6}}, + [20] = {name = "haroun", position = {x = 988, y = 1024, z = 6}}, + [21] = {name = "alesar", position = {x = 996, y = 1024, z = 6}}, + [22] = {name = "esrik", position = {x = 1000, y = 1026, z = 6}}, + [23] = {name = "yaman", position = {x = 1004, y = 1031, z = 6}}, + [24] = {name = "rashid", position = {x = 998, y = 1036, z = 6}}, + [25] = {name = "nah_bob", position = {x = 992, y = 1036, z = 6}}, + [26] = {name = "cassino", position = {x = 32354, y = 32226, z = 7}}, + [27] = {name = "tamoril", position = {x = 1013, y = 1024, z = 5}} } diff --git a/data/npc/cassino.xml b/data/npc/cassino.xml new file mode 100644 index 000000000..b1c8dc8b5 --- /dev/null +++ b/data/npc/cassino.xml @@ -0,0 +1,5 @@ + + + + + diff --git a/data/npc/scripts/custom/cassino.lua b/data/npc/scripts/custom/cassino.lua new file mode 100644 index 000000000..348c3c581 --- /dev/null +++ b/data/npc/scripts/custom/cassino.lua @@ -0,0 +1,176 @@ +local config = { + bet = { + min = 100000, -- gold coins // 30k + max = 500000, + win = 200, -- 120% high/low + winNum = 300, -- 300% numbers + }, + + playerPosition = Position(32352, 32226, 7), -- player must stay on this position to talk with npc + dicerCounter = Position(32353, 32225, 7), -- counter position +} + +local keywordHandler = KeywordHandler:new() +local npcHandler = NpcHandler:new(keywordHandler) +NpcSystem.parseParameters(npcHandler) + +function onCreatureAppear(cid) + npcHandler:onCreatureAppear(cid) +end +function onCreatureDisappear(cid) + npcHandler:onCreatureDisappear(cid) +end +function onCreatureSay(cid, type, msg) + npcHandler:onCreatureSay(cid, type, msg) +end +function onThink() + npcHandler:onThink() + local tile = Tile(config.playerPosition) + if tile then + local player = tile:getTopCreature() + if not player then + npcHandler.focuses = {} + npcHandler:updateFocus() + end + end +end + +local function getCoinValue(id) + if id == 2160 then + return 10000 + elseif id == 2152 then + return 100 + elseif id == 2148 then + return 1 + end + return 0 +end + +local function getBetValue() + local value = 0 + local tile = Tile(config.dicerCounter) + if tile then + local items = tile:getItems() + if not items or #items == 0 then + return 0 + end + + local tempMoney = {} + for _, item in pairs(items) do + if table.contains({2160, 2152, 2148}, item:getId()) then + value = value + getCoinValue(item:getId()) * item:getCount() + tempMoney[#tempMoney + 1] = item + end + end + + if value >= config.bet.min and value <= config.bet.max then -- valid bet + for _, item in pairs(tempMoney) do + item:remove() + end + return value + end + end + return nil +end + +local function createMoney(money) + local table = {} + local currentMoney = money + local crystals = math.floor(currentMoney / 10000) + currentMoney = currentMoney - crystals * 10000 + while crystals > 0 do + local count = math.min(100, crystals) + table[#table + 1] = {2160, count} + crystals = crystals - count + end + + local platinums = math.floor(currentMoney / 100) + if platinums ~= 0 then + table[#table + 1] = {2152, platinums} + currentMoney = currentMoney - platinums * 100 + end + + if currentMoney ~= 0 then + table[#table + 1] = {2148, currentMoney} + end + return table +end + +local function greetCallback(cid) + local player = Player(cid) + if player:getPosition() ~= config.playerPosition then + npcHandler:say("If you want to play with me please come near me.", cid) + return false + end + return true +end + +local function creatureSayCallback(cid, type, msg) + if not npcHandler:isFocused(cid) then + return false + end + + local player = Player(cid) + if player:getPosition() ~= config.playerPosition then + npcHandler:unGreet(cid) + return false + end + + local thisNpc = Npc(getNpcCid()) + if table.contains({"low", "high", "h", "l", "1", "2", "3", "4", "5", "6"}, msg) then + local bet = getBetValue() + if not bet then + npcHandler:say("Your bet is higher or lower than the max (".. config.bet.max ..") or min (".. config.bet.min ..") bet.", cid) + npcHandler.topic[cid] = 0 + return true + end + + local number = math.random(1, 6) + thisNpc:say(thisNpc:getName() .. " rolled a ".. number .. ".", TALKTYPE_MONSTER_SAY) + thisNpc:getPosition():sendMagicEffect(CONST_ME_CRAPS) + if table.contains({"low", "l"}, msg) then + if table.contains({1, 2, 3}, number) then + local wonMoney = bet * (config.bet.win / 100) + npcHandler:say("Congratulations, you won! Here's your (".. wonMoney ..") gold coins.", cid) + config.dicerCounter:sendMagicEffect(math.random(29, 31)) + for _, coin in pairs(createMoney(wonMoney)) do + Game.createItem(coin[1], coin[2], config.dicerCounter) + end + else + npcHandler:say("No luck this time, you lost.", cid) + end + elseif table.contains({"high", "h"}, msg) then + if table.contains({4, 5, 6}, number) then + local wonMoney = bet * (config.bet.win / 100) + npcHandler:say("Congratulations, you won! Here's your (".. wonMoney ..") gold coins.", cid) + config.dicerCounter:sendMagicEffect(math.random(29, 31)) + for _, coin in pairs(createMoney(wonMoney)) do + Game.createItem(coin[1], coin[2], config.dicerCounter) + end + else + npcHandler:say("No luck this time, you lost.", cid) + end + elseif table.contains({"1", "2", "3", "4", "5", "6"}, msg) then + if number == tonumber(msg) then + local wonMoney = bet * (config.bet.winNum / 100) + npcHandler:say("Congratulations, you won! Here's your (".. wonMoney ..") gold coins.", cid) + config.dicerCounter:sendMagicEffect(math.random(29, 31)) + for _, coin in pairs(createMoney(wonMoney)) do + Game.createItem(coin[1], coin[2], config.dicerCounter) + end + else + npcHandler:say("No luck this time, you lost.", cid) + end + end + end + return true +end + +npcHandler:setMessage(MESSAGE_GREET, "Welcome to my cassino! I'm offering {high/low} and {numbers}, to start just put your {money} on {counter} and say {number} or {high/low}.") +npcHandler:setMessage(MESSAGE_FAREWELL, 'Good bye.') +npcHandler:setMessage(MESSAGE_WALKAWAY, 'Good bye.') + +npcHandler:setCallback(CALLBACK_GREET, greetCallback) +npcHandler:setCallback(CALLBACK_MESSAGE_DEFAULT, creatureSayCallback) + +npcHandler:addModule(FocusModule:new()) diff --git a/data/scripts/custom/monster_training_machine.lua b/data/scripts/custom/monster_training_machine.lua new file mode 100644 index 000000000..37eb207d3 --- /dev/null +++ b/data/scripts/custom/monster_training_machine.lua @@ -0,0 +1,96 @@ +local mType = Game.createMonsterType("Training Machine") +local monster = {} +monster.description = "Training Machine" +monster.experience = 0 +monster.outfit = { + lookType = 1142 +} + +monster.health = 1000000 +monster.maxHealth = monster.health +monster.race = "energy" +monster.corpse = 0 +monster.speed = 0 +monster.maxSummons = 0 + +monster.changeTarget = { + interval = 1*1000, + chance = 0 +} + +monster.flags = { + summonable = false, + attackable = true, + hostile = true, + convinceable = false, + illusionable = false, + canPushItems = true, + canPushCreatures = true, + targetDistance = 1, + staticAttackChance = 100, +} + +monster.summons = { +} + +monster.voices = { + interval = 5000, + chance = 10, + {text = "I hope you are enjoying your sparring Sir or Ma'am!", yell = false}, + {text = "Threat level rising!", yell = false}, + {text = "Engaging in hostile interaction!", yell = false}, + {text = "Rrrtttarrrttarrrtta", yell = false}, + {text = "Please feel free to hit me Sir or Ma'am!", yell = false}, + {text = "klonk klonk klonk", yell = false}, + {text = "Self-diagnosis running.", yell = false}, + {text = "Battle simulation proceeding.", yell = false}, + {text = "Repairs initiated!", yell = false} +} + +monster.loot = { +} + +monster.attacks = { + {name = "melee", attack = 130, effect = CONST_ME_DRAWBLOOD, interval = 2*1000, minDamage = -1, maxDamage = -2} +} + +monster.defenses = { + defense = 1, + armor = 1 +} + +monster.elements = { +} + +monster.immunities = { +} + +--[[ +mType.onThink = function(monster, interval) + print("I'm thinking") +end + +mType.onAppear = function(monster, creature) + if monster:getId() == creature:getId() then + print(monster:getId(), creature:getId()) + end +end + +mType.onDisappear = function(monster, creature) + if monster:getId() == creature:getId() then + print(monster:getId(), creature:getId()) + end +end + +mType.onMove = function(monster, creature, fromPosition, toPosition) + if monster:getId() == creature:getId() then + print(monster:getId(), creature:getId(), fromPosition, toPosition) + end +end + +mType.onSay = function(monster, creature, type, message) + print(monster:getId(), creature:getId(), type, message) +end +]] + +mType:register(monster) diff --git a/data/scripts/custom/movement_npcs_create.lua b/data/scripts/custom/movement_npcs_create.lua new file mode 100644 index 000000000..d1110736b --- /dev/null +++ b/data/scripts/custom/movement_npcs_create.lua @@ -0,0 +1,22 @@ +local function loadCustomNpcs() + for index, value in pairs(CustomNpcTable) do + if value.name and value.position then + local spawn = Game.createNpc(value.name, value.position) + if spawn then + spawn:setMasterPos(value.position) + Game.setStorageValue(Storage.NpcSpawn, 1) + end + end + end +end + +local spawnNpcs = MoveEvent() +function spawnNpcs.onStepIn(creature, item, position, fromPosition) + if Game.getStorageValue(Storage.NpcSpawn) == -1 then + return loadCustomNpcs() + end + return true +end + +spawnNpcs:uid(25032) +spawnNpcs:register() diff --git a/data/scripts/custom/movement_trainer_entrance.lua b/data/scripts/custom/movement_trainer_entrance.lua new file mode 100644 index 000000000..403c806c9 --- /dev/null +++ b/data/scripts/custom/movement_trainer_entrance.lua @@ -0,0 +1,76 @@ +local config = { + -- Position of the first position (line 1 column 1) + firstRoomPosition = {x = 1018, y = 1112, z = 7}, + -- X distance between each room (on the same line) + distancePositionX= 12, + -- Y distance between each room (on the same line) + distancePositionY= 12, + -- Number of columns + columns= 7, + -- Number of lines + lines= 11 +} + +local function isBusyable(position) + local player = Tile(position):getTopCreature() + if player then + if player:isPlayer() then + return false + end + end + + local tile = Tile(position) + if not tile then + return false + end + + local ground = tile:getGround() + if not ground or ground:hasProperty(CONST_PROP_BLOCKSOLID) then + return false + end + + local items = tile:getItems() + for i = 1, tile:getItemCount() do + local item = items[i] + local itemType = item:getType() + if itemType:getType() ~= ITEM_TYPE_MAGICFIELD and not itemType:isMovable() and item:hasProperty(CONST_PROP_BLOCKSOLID) then + return false + end + end + return true +end + +local function calculatingRoom(uid, position, column, line) + local player = Player(uid) + if column >= config.columns then + column = 0 + line = line < (config.lines -1) and line + 1 or false + end + + if line then + local room_pos = {x = position.x + (column * config.distancePositionX), y = position.y + (line * config.distancePositionY), z = position.z} + if isBusyable(room_pos) then + player:teleportTo(room_pos) + player:getPosition():sendMagicEffect(CONST_ME_TELEPORT) + else + calculatingRoom(uid, position, column + 1, line) + end + else + player:sendCancelMessage("Couldn't find any position for you right now.") + end +end + +local trainerEntrance = MoveEvent() +function trainerEntrance.onStepIn(creature, item, position, fromPosition) + if not creature:isPlayer() then + return true + end + + calculatingRoom(creature.uid, config.firstRoomPosition, 0, 0) + Game.createMonster("training machine", creature:getPosition(), true, false) + Game.createMonster("training machine", creature:getPosition(), true, false) + return true +end + +trainerEntrance:uid(25031) +trainerEntrance:register() diff --git a/data/scripts/custom/movement_trainer_exit.lua b/data/scripts/custom/movement_trainer_exit.lua new file mode 100644 index 000000000..210a72309 --- /dev/null +++ b/data/scripts/custom/movement_trainer_exit.lua @@ -0,0 +1,30 @@ +local function removeTrainers(position) + local arrayPos = { + {x = position.x - 1, y = position.y + 1, z = position.z}, + {x = position.x + 1 , y = position.y + 1, z = position.z} + } + + for places = 1, #arrayPos do + local trainer = Tile(arrayPos[places]):getTopCreature() + if trainer then + if trainer:isMonster() then + trainer:getPosition():sendMagicEffect(CONST_ME_TELEPORT) + trainer:remove() + end + end + end +end + +local trainerExit = MoveEvent() +function trainerExit.onStepIn(creature, item, position, fromPosition) + if not creature:isPlayer() then + return true + end + + creature:teleportTo(creature:getTown():getTemplePosition()) + creature:getPosition():sendMagicEffect(CONST_ME_TELEPORT) + return true +end + +trainerExit:aid(40015) +trainerExit:register() diff --git a/data/scripts/globalevents/load_attributes.lua b/data/scripts/globalevents/load_attributes.lua deleted file mode 100644 index 5224e5464..000000000 --- a/data/scripts/globalevents/load_attributes.lua +++ /dev/null @@ -1,108 +0,0 @@ - --- This script loads the actions and uniques lib file at: data/lib/tables/action_unique.lua -local loadAttribute = GlobalEvent("AdvancedAttributesLoad") - -function loadAttribute.onStartup() - -- It load actions - for index, value in pairs(ActionTable) do - for i = 1, #value.itemPos do - local tile = Tile(value.itemPos[i]) - local item - -- Checks if the position is valid - if tile then - -- Checks that you have no items created - if tile:getItemCountById(value.itemId) == 0 then - -- If not have items created, this create the item - item = Game.createItem(value.itemId, 1, value.itemPos[i]) - end - if not item then - item = tile:getItemById(value.itemId) - end - -- If he found the item, add the action id. - if item and value.actionId then - item:setActionId(value.actionId) - end - if value.itemId == false and tile:getTopDownItem() then - tile:getTopDownItem():setActionId(value.actionId) - end - if value.itemId == false and tile:getTopTopItem() then - tile:getTopTopItem():setActionId(value.actionId) - end - -- This function add one action id on an item inside the container - -- It was developed to add action on daily respawn item - if item and value.isDailyAIDContainerItem then - itemAttr = item:addItem(value.containerItem, 1) - itemAttr:setActionId(value.actionId) - end - end - end - end - -- It load uniques - for key, value in pairs(UniqueTable) do - local tile = Tile(value.itemPos) - local item - -- Checks if the position is valid - if tile then - -- Checks that you have no items created - if tile:getItemCountById(value.itemId) == 0 then - -- If not have items created, thisc create the item - item = Game.createItem(value.itemId, 1, value.itemPos) - end - if not item then - item = tile:getItemById(value.itemId) - end - -- If he found the item, add the unique id - if item then - item:setAttribute(ITEM_ATTRIBUTE_UNIQUEID, key) - end - end - end - -- It load signs on map table - for key, value in pairs(SignTable) do - local tile = Tile(value.itemPos) - local item - -- Checks if the position is valid - if tile then - -- Checks that you have no items created - if tile:getItemCountById(value.itemId) == 0 then - -- Create item - item = Game.createItem(value.itemId, 1, value.itemPos) - end - if not item then - item = tile:getItemById(value.itemId) - end - -- If he found the item, add the text - if item then - item:setAttribute(ITEM_ATTRIBUTE_DESCRIPTION, value.text) - end - end - end - -- It load book on map table - for key, value in pairs(BookTable) do - local tile = Tile(value.itemPos) - local item - -- Checks if the position is valid - if tile then - -- Checks that you have no items created - if tile:getItemCountById(value.itemId) == 0 then - -- Create item - item = Game.createItem(value.itemId, 1, value.itemPos) - end - if not item then - item = tile:getItemById(value.itemId) - end - -- If he found the item, add the text - if item then - item:setAttribute(ITEM_ATTRIBUTE_TEXT, value.text) - end - -- This add text on book inside a container - if item and value.containerBook then - itemAttr = item:addItem(value.bookId, 1) - itemAttr:setAttribute(ITEM_ATTRIBUTE_TEXT, value.text) - end - end - end - return true -end - -loadAttribute:register() diff --git a/data/scripts/globalevents/npcs_spawn.lua b/data/scripts/globalevents/npcs_spawn.lua deleted file mode 100644 index 879b90c40..000000000 --- a/data/scripts/globalevents/npcs_spawn.lua +++ /dev/null @@ -1,17 +0,0 @@ --- This script load the file in libs/tables/npcs_spawn_list.lua) -local npcSpawn = GlobalEvent("NPCSpawnLoad") - -function npcSpawn.onStartup() - for i = 1,#NpcTable do - local npc = NpcTable[i] - if npc and npc.name and npc.position then - local spawn = Game.createNpc(npc.name, npc.position) - if spawn then - spawn:setMasterPos(npc.position) - end - end - end - return true -end - -npcSpawn:register() diff --git a/data/world/custom/otservbr-custom-houses.xml b/data/world/custom/otservbr-custom-houses.xml new file mode 100644 index 000000000..61292392c --- /dev/null +++ b/data/world/custom/otservbr-custom-houses.xml @@ -0,0 +1,5 @@ + + + + + diff --git a/data/world/custom/otservbr-custom-spawn.xml b/data/world/custom/otservbr-custom-spawn.xml new file mode 100644 index 000000000..a1cdaa81b --- /dev/null +++ b/data/world/custom/otservbr-custom-spawn.xml @@ -0,0 +1,2 @@ + + diff --git a/data/world/otservbr-spawn.xml b/data/world/otservbr-spawn.xml index 1051ba190..9997a6d70 100644 --- a/data/world/otservbr-spawn.xml +++ b/data/world/otservbr-spawn.xml @@ -11315,7 +11315,6 @@ - @@ -17809,12 +17808,6 @@ - - - - - - @@ -46025,12 +46018,6 @@ - - - - - -