| @@ -0,0 +1,143 @@ | |||
| 1 | + | local combat = Combat() | |
| 2 | + | combat:setParameter(COMBAT_PARAM_TYPE, COMBAT_PHYSICALDAMAGE) | |
| 3 | + | combat:setParameter(COMBAT_PARAM_EFFECT, 0) -- Efeito visual do ataque | |
| 4 | + | ||
| 5 | + | -- ⚡ Configuração da animação | |
| 6 | + | local FRAME_DURATION = 100 -- Tempo entre cada frame da animação | |
| 7 | + | local ANIMATION_FRAMES = { 56, 61} -- IDs da animação | |
| 8 | + | ||
| 9 | + | -- ⚡ Configuração do efeito visual com efeito e deslocamento diferente para cada direção | |
| 10 | + | local EFFECT_BY_DIRECTION = { | |
| 11 | + | [NORTH] = { effectId = 115, offset = {x = 0, y = 1} }, -- Efeito para o Norte | |
| 12 | + | [EAST] = { effectId = 114, offset = {x = 1, y = 0} }, -- Efeito para o Leste | |
| 13 | + | [SOUTH] = { effectId = 113, offset = {x = 0, y = 1} }, -- Efeito para o Sul | |
| 14 | + | [WEST] = { effectId = 116, offset = {x = 0, y = 0} } -- Efeito para o Oeste | |
| 15 | + | } | |
| 16 | + | ||
| 17 | + | -- ⚡ Configuração da storage usada como recurso | |
| 18 | + | local STORAGE_KEY = _SYSTEM.INVENTARIO[04].UID_10 -- Storage usada como custo | |
| 19 | + | local STORAGE_COST = 1 -- Quantidade a ser consumida | |
| 20 | + | ||
| 21 | + | -- ⚡ Função para virar na direção do alvo | |
| 22 | + | local function faceTarget(creature) | |
| 23 | + | local target = creature:getTarget() | |
| 24 | + | if target then | |
| 25 | + | local creaturePos = creature:getPosition() | |
| 26 | + | local targetPos = target:getPosition() | |
| 27 | + | ||
| 28 | + | if targetPos.x < creaturePos.x then | |
| 29 | + | creature:setDirection(WEST) | |
| 30 | + | elseif targetPos.x > creaturePos.x then | |
| 31 | + | creature:setDirection(EAST) | |
| 32 | + | elseif targetPos.y < creaturePos.y then | |
| 33 | + | creature:setDirection(NORTH) | |
| 34 | + | elseif targetPos.y > creaturePos.y then | |
| 35 | + | creature:setDirection(SOUTH) | |
| 36 | + | end | |
| 37 | + | end | |
| 38 | + | end | |
| 39 | + | ||
| 40 | + | -- ⚡ Cálculo do dano | |
| 41 | + | function onGetFormulaValues(player, level, maglevel) | |
| 42 | + | local min = -((level / 5) + (maglevel * 1.4) + 8) | |
| 43 | + | local max = -((level / 5) + (maglevel * 2.2) + 14) | |
| 44 | + | return min, max | |
| 45 | + | end | |
| 46 | + | combat:setCallback(CALLBACK_PARAM_LEVELMAGICVALUE, "onGetFormulaValues") | |
| 47 | + | ||
| 48 | + | -- ⚡ Função para mudar a outfit durante a animação e restaurar a original | |
| 49 | + | local function changeOutfit(cid, originalOutfit, currentFrame) | |
| 50 | + | local creature = Creature(cid) | |
| 51 | + | if not creature or not creature:isPlayer() then return end | |
| 52 | + | ||
| 53 | + | if currentFrame <= #ANIMATION_FRAMES then | |
| 54 | + | local newOutfit = { | |
| 55 | + | lookType = ANIMATION_FRAMES[currentFrame], | |
| 56 | + | lookHead = originalOutfit.lookHead, | |
| 57 | + | lookBody = originalOutfit.lookBody, | |
| 58 | + | lookLegs = originalOutfit.lookLegs, | |
| 59 | + | lookFeet = originalOutfit.lookFeet, | |
| 60 | + | lookAddons = originalOutfit.lookAddons, | |
| 61 | + | lookMount = originalOutfit.lookMount | |
| 62 | + | } | |
| 63 | + | creature:setOutfit(newOutfit) | |
| 64 | + | ||
| 65 | + | addEvent(changeOutfit, FRAME_DURATION, cid, originalOutfit, currentFrame + 1) | |
| 66 | + | else | |
| 67 | + | -- ⚡ Restaura a outfit original corretamente ao final da animação | |
| 68 | + | addEvent(function() | |
| 69 | + | local c = Creature(cid) | |
| 70 | + | if c and c:isPlayer() then | |
| 71 | + | c:setOutfit(originalOutfit) | |
| 72 | + | end | |
| 73 | + | end, FRAME_DURATION) | |
| 74 | + | end | |
| 75 | + | end | |
| 76 | + | ||
| 77 | + | -- ⚡ Função para lançar o efeito visual específico para cada direção | |
| 78 | + | local function castDirectionalEffect(creature) | |
| 79 | + | local direction = creature:getDirection() | |
| 80 | + | local pos = creature:getPosition() | |
| 81 | + | local effectData = EFFECT_BY_DIRECTION[direction] | |
| 82 | + | if effectData then | |
| 83 | + | local effectPosition = Position(pos.x + effectData.offset.x, pos.y + effectData.offset.y, pos.z) | |
| 84 | + | effectPosition:sendMagicEffect(effectData.effectId) | |
| 85 | + | end | |
| 86 | + | end | |
| 87 | + | ||
| 88 | + | -- ⚡ Função para executar múltiplos hits | |
| 89 | + | local function executeMultipleHits(creature, var, hitsRemaining) | |
| 90 | + | if hitsRemaining > 0 then | |
| 91 | + | combat:execute(creature, var) | |
| 92 | + | addEvent(function(cid, var, hits) | |
| 93 | + | local c = Creature(cid) | |
| 94 | + | if c then | |
| 95 | + | executeMultipleHits(c, var, hits) | |
| 96 | + | end | |
| 97 | + | end, 150, creature:getId(), var, hitsRemaining - 1) | |
| 98 | + | end | |
| 99 | + | end | |
| 100 | + | ||
| 101 | + | -- ⚡ Função principal da magia | |
| 102 | + | function onCastSpell(creature, var) | |
| 103 | + | if creature:isPlayer() then | |
| 104 | + | -- ⚠ Verifica cooldown baseado em storage | |
| 105 | + | local cooldownKey = 0102 -- Novo storage para evitar conflito com outras magias | |
| 106 | + | if creature:getStorageValue(cooldownKey) > os.time() then | |
| 107 | + | local remaining = creature:getStorageValue(cooldownKey) - os.time() | |
| 108 | + | creature:sendTextMessage(MESSAGE_STATUS_SMALL, "Aguarde " .. remaining .. " segundos para usar a magia novamente.") | |
| 109 | + | return false | |
| 110 | + | end | |
| 111 | + | ||
| 112 | + | -- ⚡ Verifica se há armazenamento suficiente | |
| 113 | + | local currentStorage = creature:getStorageValue(STORAGE_KEY) | |
| 114 | + | if currentStorage < STORAGE_COST then | |
| 115 | + | creature:sendTextMessage(MESSAGE_STATUS_SMALL, "Você não tem energia suficiente para usar essa magia.") | |
| 116 | + | return false | |
| 117 | + | end | |
| 118 | + | ||
| 119 | + | -- ⚡ Reduz a storage ao usar a magia | |
| 120 | + | creature:setStorageValue(STORAGE_KEY, currentStorage - STORAGE_COST) | |
| 121 | + | creature:sendCancelMessage("@LoadAmmo " .. creature:getStorageValue(STORAGE_KEY)) | |
| 122 | + | ||
| 123 | + | -- ⚡ Define cooldown de 2 segundos para essa magia | |
| 124 | + | creature:setStorageValue(cooldownKey, os.time() + 2) | |
| 125 | + | ||
| 126 | + | -- ⚡ Se houver um alvo, vira na direção dele | |
| 127 | + | faceTarget(creature) | |
| 128 | + | ||
| 129 | + | -- ⚡ Lança o efeito visual na direção do conjurador | |
| 130 | + | castDirectionalEffect(creature) | |
| 131 | + | ||
| 132 | + | -- ⚡ Salva a outfit original e inicia a animação | |
| 133 | + | local originalOutfit = creature:getOutfit() | |
| 134 | + | changeOutfit(creature:getId(), originalOutfit, 1) | |
| 135 | + | ||
| 136 | + | -- ⚡ Aplica múltiplos hits | |
| 137 | + | executeMultipleHits(creature, var, 4) | |
| 138 | + | playSound(creature, "rat_attack.ogg") | |
| 139 | + | return false | |
| 140 | + | else | |
| 141 | + | return combat:execute(creature, var) | |
| 142 | + | end | |
| 143 | + | end |
| @@ -0,0 +1,35 @@ | |||
| 1 | + | -- Defina os outfits (ajuste os lookTypes conforme seu servidor) | |
| 2 | + | local originalOutfit = {lookType = 45} -- Outfit para a voca��o 2 (normal) | |
| 3 | + | local temporaryOutfit = {lookType = 81} -- Outfit tempor�rio para God Speed (vocation 3) | |
| 4 | + | ||
| 5 | + | function onCastSpell(creature, variant) | |
| 6 | + | local player = creature:getPlayer() | |
| 7 | + | if not player then | |
| 8 | + | return false | |
| 9 | + | end | |
| 10 | + | ||
| 11 | + | -- Armazena o outfit atual do player para usar na revers�o, se desejar | |
| 12 | + | local storedOutfit = player:getOutfit() | |
| 13 | + | ||
| 14 | + | -- Altera a voca��o para 3 (God Speed) e o outfit para o tempor�rio | |
| 15 | + | player:setVocation(3) | |
| 16 | + | player:setOutfit(temporaryOutfit) | |
| 17 | + | player:sendExtendedOpcode(193, "3") | |
| 18 | + | player:sendTextMessage(MESSAGE_EVENT_ADVANCE, "Voc� ativou God Speed! (vocation 3)") | |
| 19 | + | -- Exibe um efeito visual na posi��o do player (ajuste o ID do efeito conforme seu servidor) | |
| 20 | + | player:getPosition():sendMagicEffect(121) | |
| 21 | + | ||
| 22 | + | -- Ap�s 2 minutos (120000 ms), reverte a voca��o para 2, o outfit para o original e exibe outro efeito | |
| 23 | + | addEvent(function() | |
| 24 | + | if player and player:isPlayer() then | |
| 25 | + | player:setVocation(2) | |
| 26 | + | -- Se preferir, voc� pode usar storedOutfit ou originalOutfit, conforme sua l�gica | |
| 27 | + | player:setOutfit(originalOutfit) | |
| 28 | + | player:sendExtendedOpcode(193, "2") | |
| 29 | + | player:sendTextMessage(MESSAGE_EVENT_ADVANCE, "Sua voca��o voltou ao normal.") | |
| 30 | + | player:getPosition():sendMagicEffect(121) | |
| 31 | + | end | |
| 32 | + | end, 12000) -- 120000 ms = 2 minutos | |
| 33 | + | ||
| 34 | + | return true | |
| 35 | + | end |
| @@ -0,0 +1,37 @@ | |||
| 1 | + | local vocationChangeTime = 120 -- Tempo em segundos (2 minutos) | |
| 2 | + | local newVocation = 2 -- Nova vocação temporária | |
| 3 | + | local originalOutfit = {lookType = 45} -- Outfit original | |
| 4 | + | local temporaryOutfit = {lookType = 44} -- Outfit temporário | |
| 5 | + | ||
| 6 | + | function onCastSpell(creature, variant) | |
| 7 | + | if not creature or not creature:isPlayer() then | |
| 8 | + | return false | |
| 9 | + | end | |
| 10 | + | ||
| 11 | + | local player = creature:getPlayer() | |
| 12 | + | local originalVocation = player:getVocation():getId() | |
| 13 | + | ||
| 14 | + | if originalVocation ~= 2 then | |
| 15 | + | player:sendCancelMessage("Apenas jogadores com vocation 2 podem usar essa magia.") | |
| 16 | + | return false | |
| 17 | + | end | |
| 18 | + | ||
| 19 | + | -- Altera a vocação | |
| 20 | + | player:setVocation(Vocation(newVocation)) | |
| 21 | + | -- Altera o outfit | |
| 22 | + | player:setOutfit(temporaryOutfit) | |
| 23 | + | ||
| 24 | + | -- Mensagem de feedback | |
| 25 | + | player:sendTextMessage(MESSAGE_EVENT_ADVANCE, "Sua vocação foi alterada temporariamente!") | |
| 26 | + | ||
| 27 | + | -- Reverte a mudança após o tempo definido | |
| 28 | + | addEvent(function() | |
| 29 | + | if player and player:isPlayer() then | |
| 30 | + | player:setVocation(Vocation(originalVocation)) | |
| 31 | + | player:setOutfit(originalOutfit) | |
| 32 | + | player:sendTextMessage(MESSAGE_EVENT_ADVANCE, "Sua vocação voltou ao normal.") | |
| 33 | + | end | |
| 34 | + | end, vocationChangeTime * 1000) | |
| 35 | + | ||
| 36 | + | return true | |
| 37 | + | end |
| @@ -0,0 +1,65 @@ | |||
| 1 | + | local function sendDistanceEffectDelay(cid, fromPos, toPos) | |
| 2 | + | local player = Player(cid) | |
| 3 | + | if not player then | |
| 4 | + | return | |
| 5 | + | end | |
| 6 | + | ||
| 7 | + | fromPos:sendDistanceEffect(toPos, 236) -- Efeito 236 (elétrico azul) | |
| 8 | + | end | |
| 9 | + | ||
| 10 | + | local function ninjaJumpDash(cid, targetId, oldPos, lastJump, back) | |
| 11 | + | local player = Player(cid) | |
| 12 | + | if not player then | |
| 13 | + | return | |
| 14 | + | end | |
| 15 | + | ||
| 16 | + | local target = Creature(targetId) | |
| 17 | + | if not target then | |
| 18 | + | player:setGhostMode(false) | |
| 19 | + | return | |
| 20 | + | end | |
| 21 | + | ||
| 22 | + | -- Aplica o efeito 236 no caster antes do ataque | |
| 23 | + | player:getPosition():sendMagicEffect(236) | |
| 24 | + | ||
| 25 | + | if lastJump then | |
| 26 | + | player:setGhostMode(false) | |
| 27 | + | end | |
| 28 | + | ||
| 29 | + | if back then | |
| 30 | + | player:teleportTo(oldPos) | |
| 31 | + | else | |
| 32 | + | player:teleportTo(target:getPosition()) | |
| 33 | + | end | |
| 34 | + | ||
| 35 | + | -- Aplica dano e efeito 236 no alvo | |
| 36 | + | doTargetCombatHealth(cid, target, COMBAT_ENERGYDAMAGE, -50, -150, 236) -- Dano de energia | |
| 37 | + | target:getPosition():sendMagicEffect(236) -- Efeito elétrico azul no alvo | |
| 38 | + | end | |
| 39 | + | ||
| 40 | + | function onCastSpell(creature, var) | |
| 41 | + | local cid = creature:getId() | |
| 42 | + | local playerPos = creature:getPosition() | |
| 43 | + | local target = creature:getTarget() | |
| 44 | + | ||
| 45 | + | if not target then | |
| 46 | + | creature:sendCancelMessage("Você precisa de um alvo para usar esta habilidade.") | |
| 47 | + | return false | |
| 48 | + | end | |
| 49 | + | ||
| 50 | + | creature:setGhostMode(true) | |
| 51 | + | ||
| 52 | + | -- **1º ATAQUE** | |
| 53 | + | addEvent(ninjaJumpDash, 0, cid, target:getId(), playerPos, false, false) | |
| 54 | + | addEvent(sendDistanceEffectDelay, 100, cid, playerPos, target:getPosition()) | |
| 55 | + | addEvent(sendDistanceEffectDelay, 300, cid, target:getPosition(), playerPos) | |
| 56 | + | addEvent(ninjaJumpDash, 400, cid, target:getId(), playerPos, false, true) | |
| 57 | + | ||
| 58 | + | -- **2º ATAQUE** | |
| 59 | + | addEvent(ninjaJumpDash, 600, cid, target:getId(), playerPos, false, false) | |
| 60 | + | addEvent(sendDistanceEffectDelay, 700, cid, playerPos, target:getPosition()) | |
| 61 | + | addEvent(sendDistanceEffectDelay, 1000, cid, target:getPosition(), playerPos) | |
| 62 | + | addEvent(ninjaJumpDash, 1100, cid, target:getId(), playerPos, true, true) | |
| 63 | + | playSound(creature, "energy.ogg") | |
| 64 | + | return false | |
| 65 | + | end |
| @@ -0,0 +1,192 @@ | |||
| 1 | + | -- Configurações da animação | |
| 2 | + | local FRAME_DURATION = 100 -- Duração de cada frame em milissegundos | |
| 3 | + | local ANIMATION_FRAMES = { | |
| 4 | + | 73, -- Frame (substitua pelos IDs corretos das outfits) | |
| 5 | + | 74, -- Frame | |
| 6 | + | 75, -- Frame | |
| 7 | + | 76, -- Frame | |
| 8 | + | 77, -- Frame | |
| 9 | + | 78, | |
| 10 | + | 45 -- Frame | |
| 11 | + | ||
| 12 | + | } | |
| 13 | + | ||
| 14 | + | -- Configurações do item temporário | |
| 15 | + | local tempItemId = 9078 -- ID do item temporário | |
| 16 | + | local tempItemDuration = 600 -- Tempo que o item fica no chão (230ms) | |
| 17 | + | ||
| 18 | + | -- Função que troca a outfit frame por frame | |
| 19 | + | local function changeOutfit(cid, originalOutfit, currentFrame) | |
| 20 | + | local creature = Player(cid) | |
| 21 | + | if not creature or not creature:isPlayer() then | |
| 22 | + | return | |
| 23 | + | end | |
| 24 | + | ||
| 25 | + | if currentFrame <= #ANIMATION_FRAMES then | |
| 26 | + | local newOutfit = { | |
| 27 | + | lookType = ANIMATION_FRAMES[currentFrame], | |
| 28 | + | lookHead = originalOutfit.lookHead, | |
| 29 | + | lookBody = originalOutfit.lookBody, | |
| 30 | + | lookLegs = originalOutfit.lookLegs, | |
| 31 | + | lookFeet = originalOutfit.lookFeet, | |
| 32 | + | lookAddons = originalOutfit.lookAddons, | |
| 33 | + | lookMount = originalOutfit.lookMount | |
| 34 | + | } | |
| 35 | + | creature:setOutfit(newOutfit) | |
| 36 | + | -- Agenda o próximo frame da animação | |
| 37 | + | addEvent(changeOutfit, FRAME_DURATION, cid, originalOutfit, currentFrame + 1) | |
| 38 | + | end | |
| 39 | + | -- A restauração da outfit original será feita somente ao sair da magia. | |
| 40 | + | end | |
| 41 | + | ||
| 42 | + | -- Funções do efeito mágico | |
| 43 | + | local function targetEffect(cid) | |
| 44 | + | local player = Player(cid) | |
| 45 | + | if not player then | |
| 46 | + | return | |
| 47 | + | end | |
| 48 | + | ||
| 49 | + | local effect = 237 -- Efeito elétrico azul | |
| 50 | + | local orig = player:getPosition() | |
| 51 | + | local d1, d2 = {z = orig.z}, {z = orig.z} | |
| 52 | + | ||
| 53 | + | d1.x = orig.x - 5 | |
| 54 | + | d2.x = orig.x + 5 | |
| 55 | + | for i = -2, 2 do | |
| 56 | + | d1.y = orig.y + i | |
| 57 | + | d2.y = d1.y | |
| 58 | + | orig:sendDistanceEffect(d1, effect) | |
| 59 | + | orig:sendDistanceEffect(d2, effect) | |
| 60 | + | end | |
| 61 | + | ||
| 62 | + | d1.y = orig.y - 3 | |
| 63 | + | d2.y = orig.y + 3 | |
| 64 | + | for i = -4, 4 do | |
| 65 | + | d1.x = orig.x + i | |
| 66 | + | d2.x = d1.x | |
| 67 | + | orig:sendDistanceEffect(d1, effect) | |
| 68 | + | orig:sendDistanceEffect(d2, effect) | |
| 69 | + | end | |
| 70 | + | end | |
| 71 | + | ||
| 72 | + | -- Função que retorna o jogador para a posição original, desativa ghost mode e restaura a outfit original | |
| 73 | + | local function backOldPosition(cid, oldPosition, originalOutfit) | |
| 74 | + | local player = Player(cid) | |
| 75 | + | if not player then | |
| 76 | + | return | |
| 77 | + | end | |
| 78 | + | ||
| 79 | + | player:teleportTo(oldPosition) | |
| 80 | + | player:setGhostMode(false) | |
| 81 | + | player:setOutfit(originalOutfit) | |
| 82 | + | -- Removido: player:setMovementBlocked(false) | |
| 83 | + | end | |
| 84 | + | ||
| 85 | + | local function jumpEffect(cid, target) | |
| 86 | + | local player = Player(cid) | |
| 87 | + | if not player then | |
| 88 | + | return | |
| 89 | + | end | |
| 90 | + | ||
| 91 | + | local targetCreature = Creature(target) | |
| 92 | + | if targetCreature then | |
| 93 | + | player:getPosition():sendDistanceEffect(targetCreature:getPosition(), 237) | |
| 94 | + | end | |
| 95 | + | end | |
| 96 | + | ||
| 97 | + | local function extractRandomValuesFromTable(tbl) | |
| 98 | + | if #tbl == 0 then | |
| 99 | + | return false | |
| 100 | + | end | |
| 101 | + | return table.remove(tbl, math.random(#tbl)) | |
| 102 | + | end | |
| 103 | + | ||
| 104 | + | -- Modificada para receber originalOutfit e exibir o effect 237 enquanto pula, | |
| 105 | + | -- além de criar e remover o item temporário no alvo atingido. | |
| 106 | + | local function jumpOnTarget(cid, target, targetCount, oldPosition, originalOutfit) | |
| 107 | + | local player = Player(cid) | |
| 108 | + | if not player then | |
| 109 | + | return | |
| 110 | + | end | |
| 111 | + | ||
| 112 | + | local targetCreature = Creature(target) | |
| 113 | + | if targetCreature then | |
| 114 | + | addEvent(targetEffect, 100, cid) | |
| 115 | + | player:teleportTo(targetCreature:getPosition()) | |
| 116 | + | player:setGhostMode(true) | |
| 117 | + | -- Exibe o effect 237 enquanto pula para o novo alvo | |
| 118 | + | player:getPosition():sendMagicEffect(237) | |
| 119 | + | targetCreature:getPosition():sendMagicEffect(237) | |
| 120 | + | doTargetCombatHealth(cid, targetCreature, COMBAT_ENERGYDAMAGE, -50, -150, CONST_ME_ENERGYHIT) | |
| 121 | + | ||
| 122 | + | -- Cria o item temporário no local do alvo atingido e agenda sua remoção | |
| 123 | + | local tempItem = Game.createItem(tempItemId, 1, targetCreature:getPosition()) | |
| 124 | + | if tempItem then | |
| 125 | + | addEvent(function(pos) | |
| 126 | + | local tile = Tile(pos) | |
| 127 | + | if tile then | |
| 128 | + | local item = tile:getItemById(tempItemId) | |
| 129 | + | if item then | |
| 130 | + | item:remove() | |
| 131 | + | end | |
| 132 | + | end | |
| 133 | + | end, tempItemDuration, targetCreature:getPosition()) | |
| 134 | + | end | |
| 135 | + | ||
| 136 | + | if targetCount == 0 then | |
| 137 | + | addEvent(backOldPosition, 400, cid, oldPosition, originalOutfit) | |
| 138 | + | end | |
| 139 | + | end | |
| 140 | + | end | |
| 141 | + | ||
| 142 | + | -- Função principal do feitiço | |
| 143 | + | function onCastSpell(creature, var) | |
| 144 | + | local cid = creature:getId() | |
| 145 | + | local originalPos = creature:getPosition() | |
| 146 | + | local originalOutfit = creature:getOutfit() | |
| 147 | + | ||
| 148 | + | -- Removida: Bloqueia o movimento do jogador enquanto durar a magia | |
| 149 | + | -- creature:setMovementBlocked(true) | |
| 150 | + | ||
| 151 | + | -- Ajusta o eixo para o efeito 192 antes da animação (exemplo, ajuste conforme necessário) | |
| 152 | + | local pos = creature:getPosition() | |
| 153 | + | pos.x = pos.x + 1 | |
| 154 | + | pos.y = pos.y | |
| 155 | + | pos:sendMagicEffect(191) | |
| 156 | + | ||
| 157 | + | -- Inicia a animação de troca de outfit frame por frame | |
| 158 | + | changeOutfit(cid, originalOutfit, 1) | |
| 159 | + | ||
| 160 | + | -- Agenda a execução do feitiço após o término da animação | |
| 161 | + | addEvent(function() | |
| 162 | + | local targets = {} | |
| 163 | + | local playerPos = creature:getPosition() | |
| 164 | + | ||
| 165 | + | -- Efeitos ao ativar a magia | |
| 166 | + | playerPos:sendMagicEffect(236) | |
| 167 | + | -- Obtém os espectadores dentro de um raio de 5x5 | |
| 168 | + | local spectators = Game.getSpectators(playerPos, false, false, 5, 5, 5, 5) | |
| 169 | + | for i = 1, #spectators do | |
| 170 | + | local specs = spectators[i] | |
| 171 | + | if specs ~= creature and not specs:isNpc() and playerPos:getDistance(specs:getPosition()) <= 5 then | |
| 172 | + | targets[#targets + 1] = specs | |
| 173 | + | end | |
| 174 | + | end | |
| 175 | + | ||
| 176 | + | if #targets == 0 then | |
| 177 | + | creature:sendCancelMessage('There are no targets in range (5x5).') | |
| 178 | + | playerPos:sendMagicEffect(CONST_ME_POFF) | |
| 179 | + | -- Removida: creature:setMovementBlocked(false) | |
| 180 | + | return false | |
| 181 | + | end | |
| 182 | + | ||
| 183 | + | local targetCount = #targets | |
| 184 | + | for i = 1, #targets do | |
| 185 | + | local randTarget = extractRandomValuesFromTable(targets) | |
| 186 | + | addEvent(jumpOnTarget, i * 200, cid, randTarget:getId(), targetCount - i, originalPos, originalOutfit) | |
| 187 | + | addEvent(jumpEffect, i * 400, cid, randTarget:getId()) | |
| 188 | + | end | |
| 189 | + | end, (#ANIMATION_FRAMES + 1) * FRAME_DURATION) | |
| 190 | + | playSound(creature, "energy.ogg") | |
| 191 | + | return false | |
| 192 | + | end |
| @@ -0,0 +1,95 @@ | |||
| 1 | + | local combat = createCombatObject() | |
| 2 | + | -- Define o tipo de dano azul (energia) e os efeitos visuais | |
| 3 | + | setCombatParam(combat, COMBAT_PARAM_TYPE, COMBAT_ENERGYDAMAGE) | |
| 4 | + | setCombatParam(combat, COMBAT_PARAM_EFFECT, 100) | |
| 5 | + | setCombatParam(combat, COMBAT_PARAM_DISTANCEEFFECT, 0) | |
| 6 | + | ||
| 7 | + | -- Define a fórmula de dano para causar 100 de dano (constante) | |
| 8 | + | -- Fórmula: dano mínimo = (level * 0) - 100 e dano máximo = (level * 0) - 100 | |
| 9 | + | setCombatFormula(combat, COMBAT_FORMULA_LEVELMAGIC, 0, -100, 0, -100) | |
| 10 | + | ||
| 11 | + | -- Cria a área de efeito 5x5 com o centro marcado como "2" | |
| 12 | + | local area = createCombatArea({ | |
| 13 | + | {1, 1, 1, 1, 1}, | |
| 14 | + | {1, 1, 1, 1, 1}, | |
| 15 | + | {1, 1, 2, 1, 1}, | |
| 16 | + | {1, 1, 1, 1, 1}, | |
| 17 | + | {1, 1, 1, 1, 1} | |
| 18 | + | }) | |
| 19 | + | setCombatArea(combat, area) | |
| 20 | + | ||
| 21 | + | -- Função para manter o efeito visual reaplicando-o a cada 'interval' ms | |
| 22 | + | local function persistEffect(pos, effectId, interval, stopFlag) | |
| 23 | + | if not stopFlag.value then | |
| 24 | + | doSendMagicEffect(pos, effectId) | |
| 25 | + | addEvent(persistEffect, interval, pos, effectId, interval, stopFlag) | |
| 26 | + | end | |
| 27 | + | end | |
| 28 | + | ||
| 29 | + | function onCastSpell(creature, var) | |
| 30 | + | local casterPos = getCreaturePosition(creature) | |
| 31 | + | ||
| 32 | + | -- Troca o looktype para 43 no início da conjuração | |
| 33 | + | doCreatureChangeOutfit(creature, {lookType = 43}) | |
| 34 | + | ||
| 35 | + | -- Calcula a posição central onde a área 5x5 será aplicada | |
| 36 | + | local areaPos = {x = casterPos.x + 4, y = casterPos.y + 4, z = casterPos.z} | |
| 37 | + | -- Cria o objeto Variant que une a posição do conjurador com a área 5x5 | |
| 38 | + | local variant = Variant(casterPos, area) | |
| 39 | + | ||
| 40 | + | -- Cria a condição de slow (60% de redução de velocidade) | |
| 41 | + | local slowCondition = createConditionObject(CONDITION_HASTE) | |
| 42 | + | setConditionParam(slowCondition, CONDITION_PARAM_SPEEDPERCENT, -60) | |
| 43 | + | -- Define a duração para cobrir toda a conjuração (por exemplo, 3000ms) | |
| 44 | + | setConditionParam(slowCondition, CONDITION_PARAM_TICKS, 3000) | |
| 45 | + | ||
| 46 | + | -- Aplica a condição slow e o efeito 85 aos alvos presentes na área (exceto o conjurador) | |
| 47 | + | for dx = -2, 2 do | |
| 48 | + | for dy = -2, 2 do | |
| 49 | + | local pos = {x = areaPos.x + dx, y = areaPos.y + dy, z = areaPos.z} | |
| 50 | + | local target = getTopCreature(pos) | |
| 51 | + | if target and target.uid ~= creature.uid then | |
| 52 | + | doAddCondition(target, slowCondition) | |
| 53 | + | doSendMagicEffect(getCreaturePosition(target), 85) | |
| 54 | + | end | |
| 55 | + | end | |
| 56 | + | end | |
| 57 | + | ||
| 58 | + | local stopFlag = {value = false} | |
| 59 | + | ||
| 60 | + | -- Inicia o efeito 102 na área, reaplicando-o a cada 600ms | |
| 61 | + | persistEffect(areaPos, 96, 1000, stopFlag) | |
| 62 | + | ||
| 63 | + | -- Aguarda 2 segundos para que o efeito 102 permaneça visível | |
| 64 | + | addEvent(function() | |
| 65 | + | stopFlag.value = true -- Para o loop do efeito 102 | |
| 66 | + | ||
| 67 | + | local damageIntervals = {0, 300, 600, 900} -- intervalos após os 2 segundos | |
| 68 | + | local damageEffects = {94, 237, 237, 237} -- efeitos a serem exibidos com cada dano | |
| 69 | + | local effectOffsets = { | |
| 70 | + | {x = 0, y = -3}, -- desloca o effect 97 | |
| 71 | + | {x = -3, y = -3}, -- desloca o effect 98 | |
| 72 | + | {x = -3, y = -3}, -- desloca o effect 103 | |
| 73 | + | {x = -3, y = -3} -- desloca o effect 99 | |
| 74 | + | } | |
| 75 | + | ||
| 76 | + | for i, delay in ipairs(damageIntervals) do | |
| 77 | + | addEvent(function() | |
| 78 | + | local effectPos = { | |
| 79 | + | x = areaPos.x + effectOffsets[i].x, | |
| 80 | + | y = areaPos.y + effectOffsets[i].y, | |
| 81 | + | z = areaPos.z | |
| 82 | + | } | |
| 83 | + | doSendMagicEffect(effectPos, damageEffects[i]) | |
| 84 | + | doCombat(creature, combat, variant) | |
| 85 | + | end, delay) | |
| 86 | + | end | |
| 87 | + | ||
| 88 | + | -- Após o último efeito, troca o looktype para 45 no final da conjuração | |
| 89 | + | addEvent(function() | |
| 90 | + | doCreatureChangeOutfit(creature, {lookType = 81}) | |
| 91 | + | end, 1000) | |
| 92 | + | end, 1000) | |
| 93 | + | ||
| 94 | + | return true | |
| 95 | + | end |
| @@ -0,0 +1,131 @@ | |||
| 1 | + | -- Fun��o para mostrar o efeito centralizado no jogador | |
| 2 | + | local function showEffectCenter(creature, effect) | |
| 3 | + | if creature and not creature:isRemoved() then | |
| 4 | + | print("Efeito Centralizado: ", effect) -- Debug | |
| 5 | + | creature:getPosition():sendMagicEffect(effect) | |
| 6 | + | end | |
| 7 | + | end | |
| 8 | + | ||
| 9 | + | -- Fun��o para exibir efeitos com reposicionamento do eixo | |
| 10 | + | local function showEffectAtOffset(creature, effect, offset) | |
| 11 | + | if creature and not creature:isRemoved() then | |
| 12 | + | local pos = creature:getPosition() | |
| 13 | + | pos.x = pos.x + offset.x | |
| 14 | + | pos.y = pos.y + offset.y | |
| 15 | + | print("Efeito Offset: ", effect, " na posi��o ", pos.x, pos.y) -- Debug | |
| 16 | + | pos:sendMagicEffect(effect) | |
| 17 | + | end | |
| 18 | + | end | |
| 19 | + | ||
| 20 | + | -- Fun��o para aplicar o efeito 32 em jogadores paralisados por 2 segundos | |
| 21 | + | local function applyParalysisEffect(target) | |
| 22 | + | local duration = 2000 -- Dura��o total do efeito: 2 segundos | |
| 23 | + | local interval = 200 -- Intervalo entre as anima�es: 200ms | |
| 24 | + | local effect = 237 -- Efeito a ser exibido | |
| 25 | + | ||
| 26 | + | for i = 0, duration, interval do | |
| 27 | + | addEvent(function() | |
| 28 | + | if target and not target:isRemoved() then | |
| 29 | + | target:getPosition():sendMagicEffect(effect) | |
| 30 | + | end | |
| 31 | + | end, i) | |
| 32 | + | end | |
| 33 | + | end | |
| 34 | + | ||
| 35 | + | -- Fun��o para aplicar dano em �rea (5x5) ao redor da criatura, com paralisia | |
| 36 | + | local function applyAreaDamage(creature) | |
| 37 | + | local pos = creature:getPosition() | |
| 38 | + | local damage = -100 | |
| 39 | + | local effect = 236 | |
| 40 | + | ||
| 41 | + | -- Configura��o da condi��o de paralisia por 3 segundos | |
| 42 | + | local paralysis = Condition(CONDITION_PARALYZE) | |
| 43 | + | paralysis:setParameter(CONDITION_PARAM_TICKS, 3000) | |
| 44 | + | paralysis:setParameter(CONDITION_PARAM_SPEED, -1000) | |
| 45 | + | ||
| 46 | + | for x = -2, 2 do | |
| 47 | + | for y = -2, 2 do | |
| 48 | + | local targetPos = Position(pos.x + x, pos.y + y, pos.z) | |
| 49 | + | targetPos:sendMagicEffect(effect) | |
| 50 | + | ||
| 51 | + | local tile = Tile(targetPos) | |
| 52 | + | if tile then | |
| 53 | + | local target = tile:getTopCreature() | |
| 54 | + | if target and target ~= creature then | |
| 55 | + | target:addHealth(damage) | |
| 56 | + | target:addCondition(paralysis) | |
| 57 | + | applyParalysisEffect(target) | |
| 58 | + | end | |
| 59 | + | end | |
| 60 | + | end | |
| 61 | + | end | |
| 62 | + | end | |
| 63 | + | ||
| 64 | + | function onCastSpell(creature, var) | |
| 65 | + | local waittime = 1 | |
| 66 | + | local storage = 99916 | |
| 67 | + | ||
| 68 | + | if creature:getStorageValue(storage) > os.time() then | |
| 69 | + | creature:sendCancelMessage("Voc� s� pode usar esta magia novamente em [" .. | |
| 70 | + | (creature:getStorageValue(storage) - os.time()) .. "] segundos.") | |
| 71 | + | return false | |
| 72 | + | end | |
| 73 | + | ||
| 74 | + | creature:setStorageValue(storage, os.time() + waittime) | |
| 75 | + | local originalOutfit = creature:getOutfit() | |
| 76 | + | ||
| 77 | + | -- Define as outfits para os frames da magia | |
| 78 | + | local outfits = { | |
| 79 | + | {lookType = 73}, {lookType = 74}, {lookType = 75}, {lookType = 76}, | |
| 80 | + | {lookType = 77}, {lookType = 78}, {lookType = 79}, {lookType = 80}, | |
| 81 | + | {lookType = 79}, {lookType = 80}, {lookType = 79}, {lookType = 80}, | |
| 82 | + | {lookType = 79}, {lookType = 80}, {lookType = 79}, {lookType = 45} | |
| 83 | + | } | |
| 84 | + | ||
| 85 | + | -- IDs dos efeitos para teste (use IDs conhecidos: 1 ou 2) | |
| 86 | + | local effect1 = {id = 237, offset = {x = 0, y = 0}} -- Testando com ID 1 | |
| 87 | + | local effect2 = {id = 237, offset = {x = 0, y = 0}} -- Testando com ID 2 | |
| 88 | + | local effectCenterId = 208 -- ID do efeito centralizado (confira se � v�lido) | |
| 89 | + | ||
| 90 | + | -- Teste: Mostra o efeito centralizado | |
| 91 | + | addEvent(function() | |
| 92 | + | showEffectCenter(creature, effectCenterId) | |
| 93 | + | end, 0) | |
| 94 | + | ||
| 95 | + | -- Teste: Mostra os efeitos com offset | |
| 96 | + | addEvent(function() | |
| 97 | + | showEffectAtOffset(creature, effect1.id, effect1.offset) | |
| 98 | + | showEffectAtOffset(creature, effect2.id, effect2.offset) | |
| 99 | + | end, 300) | |
| 100 | + | ||
| 101 | + | -- Aplica o dano na �rea ampliada (5x5) ap�s 1s | |
| 102 | + | addEvent(function() | |
| 103 | + | if not creature or creature:isRemoved() then return end | |
| 104 | + | applyAreaDamage(creature) | |
| 105 | + | end, 700) | |
| 106 | + | ||
| 107 | + | -- Troca os outfits durante a execu��o da magia | |
| 108 | + | for i = 1, #outfits do | |
| 109 | + | addEvent(function() | |
| 110 | + | if creature and not creature:isRemoved() then | |
| 111 | + | creature:setOutfit(outfits[i]) | |
| 112 | + | end | |
| 113 | + | end, (i - 1) * 80) | |
| 114 | + | end | |
| 115 | + | ||
| 116 | + | -- Restaura o outfit original | |
| 117 | + | addEvent(function() | |
| 118 | + | if creature and not creature:isRemoved() then | |
| 119 | + | creature:setOutfit(originalOutfit) | |
| 120 | + | end | |
| 121 | + | end, (#outfits * 100) + 100) | |
| 122 | + | ||
| 123 | + | -- Reposiciona o som para tocar ap�s todos os efeitos | |
| 124 | + | addEvent(function() | |
| 125 | + | if creature and not creature:isRemoved() then | |
| 126 | + | -- playSound(creature, "woodcutting.ogg") | |
| 127 | + | end | |
| 128 | + | end, 0) | |
| 129 | + | playSound(creature, "energy.ogg") | |
| 130 | + | return false | |
| 131 | + | end |
| @@ -0,0 +1,61 @@ | |||
| 1 | + | local combat = createCombatObject() | |
| 2 | + | ||
| 3 | + | -- Configura�es do buff | |
| 4 | + | local buffDuration = 5000 -- Dura��o total do buff (5 segundos) | |
| 5 | + | local tickInterval = 1000 -- Intervalo entre os ticks (1 segundo) | |
| 6 | + | local ticks = 4 -- Quantidade de ticks (4 vezes, 25 HP cada, totalizando 100 HP) | |
| 7 | + | local manaPercentPerTick = 0.10 -- Percentual de mana restaurada por tick (10%) | |
| 8 | + | local baseHpPerTick = 50 -- Cura base por tick (25 HP) | |
| 9 | + | local levelScaling = 0.05 -- Aumento de 5% na cura a cada 10 n�veis | |
| 10 | + | ||
| 11 | + | -- Deslocamento para os efeitos visuais (ajuste conforme necess�rio) | |
| 12 | + | local offsetX = 1 -- +1 para direita, -1 para esquerda | |
| 13 | + | local offsetY = 0 -- +1 para baixo, -1 para cima | |
| 14 | + | ||
| 15 | + | function onCastSpell(creature, var) | |
| 16 | + | local maxMana = creature:getMaxMana() | |
| 17 | + | local restorePerTick = math.floor(maxMana * manaPercentPerTick) -- 10% da mana m�xima por tick | |
| 18 | + | local level = creature:getLevel() -- Pega o n�vel do conjurador | |
| 19 | + | local tickCount = 0 | |
| 20 | + | ||
| 21 | + | -- Calcula a cura de HP ajustada pelo n�vel | |
| 22 | + | local adjustedHpPerTick = math.floor(baseHpPerTick * (1 + math.floor(level / 10) * levelScaling)) | |
| 23 | + | ||
| 24 | + | -- Fun��o que restaura a mana e cura HP a cada tick | |
| 25 | + | local function restoreManaAndHp(creatureId) | |
| 26 | + | local creature = Creature(creatureId) | |
| 27 | + | if not creature then | |
| 28 | + | return | |
| 29 | + | end | |
| 30 | + | ||
| 31 | + | tickCount = tickCount + 1 | |
| 32 | + | creature:addMana(restorePerTick) -- Restaura a mana | |
| 33 | + | creature:addHealth(adjustedHpPerTick) -- Cura HP ajustado pelo n�vel | |
| 34 | + | ||
| 35 | + | -- Pega a posi��o atual do conjurador em cada tick | |
| 36 | + | local playerPos = creature:getPosition() | |
| 37 | + | ||
| 38 | + | -- Calcula as novas posi�es para os efeitos visuais em rela��o ao jogador | |
| 39 | + | local effectPos1 = Position(playerPos.x + offsetX, playerPos.y + offsetY, playerPos.z) | |
| 40 | + | local effectPos2 = Position(playerPos.x + 2 - offsetX, playerPos.y - offsetY, playerPos.z) | |
| 41 | + | ||
| 42 | + | -- Aplica os efeitos visuais nas posi�es ajustadas | |
| 43 | + | effectPos1:sendMagicEffect(191) | |
| 44 | + | effectPos2:sendMagicEffect(192) | |
| 45 | + | ||
| 46 | + | -- Continua restaurando mana e curando HP at� que todos os ticks sejam completados | |
| 47 | + | if tickCount < ticks then | |
| 48 | + | addEvent(restoreManaAndHp, tickInterval, creatureId) | |
| 49 | + | else | |
| 50 | + | end | |
| 51 | + | end | |
| 52 | + | ||
| 53 | + | -- Inicia o buff de mana e cura | |
| 54 | + | addEvent(restoreManaAndHp, tickInterval, creature:getId()) | |
| 55 | + | ||
| 56 | + | -- Aplica o efeito 193 com o eixo ajustado | |
| 57 | + | local adjustedPos = Position(creature:getPosition().x + offsetX, creature:getPosition().y + offsetY, creature:getPosition().z) | |
| 58 | + | adjustedPos:sendMagicEffect(191) | |
| 59 | + | ||
| 60 | + | return false | |
| 61 | + | end |
| @@ -0,0 +1,95 @@ | |||
| 1 | + | local combat = createCombatObject() | |
| 2 | + | -- Define o tipo de dano azul (energia) e os efeitos visuais | |
| 3 | + | setCombatParam(combat, COMBAT_PARAM_TYPE, COMBAT_ENERGYDAMAGE) | |
| 4 | + | setCombatParam(combat, COMBAT_PARAM_EFFECT, 100) | |
| 5 | + | setCombatParam(combat, COMBAT_PARAM_DISTANCEEFFECT, 0) | |
| 6 | + | ||
| 7 | + | -- Define a f�rmula de dano para causar 100 de dano (constante) | |
| 8 | + | -- F�rmula: dano m�nimo = (level * 0) - 100 e dano m�ximo = (level * 0) - 100 | |
| 9 | + | setCombatFormula(combat, COMBAT_FORMULA_LEVELMAGIC, 0, -100, 0, -100) | |
| 10 | + | ||
| 11 | + | -- Cria a �rea de efeito 5x5 com o centro marcado como "2" | |
| 12 | + | local area = createCombatArea({ | |
| 13 | + | {1, 1, 1, 1, 1}, | |
| 14 | + | {1, 1, 1, 1, 1}, | |
| 15 | + | {1, 1, 2, 1, 1}, | |
| 16 | + | {1, 1, 1, 1, 1}, | |
| 17 | + | {1, 1, 1, 1, 1} | |
| 18 | + | }) | |
| 19 | + | setCombatArea(combat, area) | |
| 20 | + | ||
| 21 | + | -- Fun��o para manter o efeito visual reaplicando-o a cada 'interval' ms | |
| 22 | + | local function persistEffect(pos, effectId, interval, stopFlag) | |
| 23 | + | if not stopFlag.value then | |
| 24 | + | doSendMagicEffect(pos, effectId) | |
| 25 | + | addEvent(persistEffect, interval, pos, effectId, interval, stopFlag) | |
| 26 | + | end | |
| 27 | + | end | |
| 28 | + | ||
| 29 | + | function onCastSpell(creature, var) | |
| 30 | + | local casterPos = getCreaturePosition(creature) | |
| 31 | + | ||
| 32 | + | -- Troca o looktype para 43 no in�cio da conjura��o | |
| 33 | + | doCreatureChangeOutfit(creature, {lookType = 43}) | |
| 34 | + | ||
| 35 | + | -- Calcula a posi��o central onde a �rea 5x5 ser� aplicada | |
| 36 | + | local areaPos = {x = casterPos.x + 4, y = casterPos.y + 4, z = casterPos.z} | |
| 37 | + | -- Cria o objeto Variant que une a posi��o do conjurador com a �rea 5x5 | |
| 38 | + | local variant = Variant(casterPos, area) | |
| 39 | + | ||
| 40 | + | -- Cria a condi��o de slow (60% de redu��o de velocidade) | |
| 41 | + | local slowCondition = createConditionObject(CONDITION_HASTE) | |
| 42 | + | setConditionParam(slowCondition, CONDITION_PARAM_SPEEDPERCENT, -60) | |
| 43 | + | -- Define a dura��o para cobrir toda a conjura��o (por exemplo, 3000ms) | |
| 44 | + | setConditionParam(slowCondition, CONDITION_PARAM_TICKS, 3000) | |
| 45 | + | ||
| 46 | + | -- Aplica a condi��o slow e o efeito 85 aos alvos presentes na �rea (exceto o conjurador) | |
| 47 | + | for dx = -2, 2 do | |
| 48 | + | for dy = -2, 2 do | |
| 49 | + | local pos = {x = areaPos.x + dx, y = areaPos.y + dy, z = areaPos.z} | |
| 50 | + | local target = getTopCreature(pos) | |
| 51 | + | if target and target.uid ~= creature.uid then | |
| 52 | + | doAddCondition(target, slowCondition) | |
| 53 | + | doSendMagicEffect(getCreaturePosition(target), 85) | |
| 54 | + | end | |
| 55 | + | end | |
| 56 | + | end | |
| 57 | + | ||
| 58 | + | local stopFlag = {value = false} | |
| 59 | + | ||
| 60 | + | -- Inicia o efeito 102 na �rea, reaplicando-o a cada 600ms | |
| 61 | + | persistEffect(areaPos, 102, 600, stopFlag) | |
| 62 | + | ||
| 63 | + | -- Aguarda 2 segundos para que o efeito 102 permane�a vis�vel | |
| 64 | + | addEvent(function() | |
| 65 | + | stopFlag.value = true -- Para o loop do efeito 102 | |
| 66 | + | ||
| 67 | + | local damageIntervals = {0, 500, 1000, 1500} -- intervalos ap�s os 2 segundos | |
| 68 | + | local damageEffects = {97, 98, 103, 99} -- efeitos a serem exibidos com cada dano | |
| 69 | + | local effectOffsets = { | |
| 70 | + | {x = -3, y = -3}, -- desloca o effect 97 | |
| 71 | + | {x = -3, y = -3}, -- desloca o effect 98 | |
| 72 | + | {x = -3, y = -3}, -- desloca o effect 103 | |
| 73 | + | {x = -3, y = -3} -- desloca o effect 99 | |
| 74 | + | } | |
| 75 | + | ||
| 76 | + | for i, delay in ipairs(damageIntervals) do | |
| 77 | + | addEvent(function() | |
| 78 | + | local effectPos = { | |
| 79 | + | x = areaPos.x + effectOffsets[i].x, | |
| 80 | + | y = areaPos.y + effectOffsets[i].y, | |
| 81 | + | z = areaPos.z | |
| 82 | + | } | |
| 83 | + | doSendMagicEffect(effectPos, damageEffects[i]) | |
| 84 | + | doCombat(creature, combat, variant) | |
| 85 | + | end, delay) | |
| 86 | + | end | |
| 87 | + | ||
| 88 | + | -- Ap�s o �ltimo efeito, troca o looktype para 45 no final da conjura��o | |
| 89 | + | addEvent(function() | |
| 90 | + | doCreatureChangeOutfit(creature, {lookType = 45}) | |
| 91 | + | end, 1500) | |
| 92 | + | end, 1000) | |
| 93 | + | ||
| 94 | + | return true | |
| 95 | + | end |
| @@ -0,0 +1,23 @@ | |||
| 1 | + | function onCastSpell(creature, var) | |
| 2 | + | local player = Player(creature:getId()) | |
| 3 | + | if not player then | |
| 4 | + | return false | |
| 5 | + | end | |
| 6 | + | ||
| 7 | + | -- Ativa Ghost Mode (invisibilidade) | |
| 8 | + | player:setGhostMode(true) | |
| 9 | + | -- Exibe um efeito visual inicial (opcional, use o que preferir) | |
| 10 | + | player:getPosition():sendMagicEffect(237) | |
| 11 | + | ||
| 12 | + | -- Ap�s 3 segundos, remove Ghost Mode e aplica dano em �rea com efeito 65 | |
| 13 | + | addEvent(function() | |
| 14 | + | if player and player:isPlayer() then | |
| 15 | + | player:setGhostMode(false) | |
| 16 | + | local pos = player:getPosition() | |
| 17 | + | -- Aplica dano em �rea: ajuste os valores de dano conforme necess�rio. | |
| 18 | + | doAreaCombatHealth(player:getId(), COMBAT_ENERGYDAMAGE, pos, AREA_SQUARE3, -100, -300, 65) | |
| 19 | + | end | |
| 20 | + | end, 3000) | |
| 21 | + | ||
| 22 | + | return false | |
| 23 | + | end |
| @@ -0,0 +1,202 @@ | |||
| 1 | + | local combat = Combat() -- Cria o objeto de combate | |
| 2 | + | combat:setParameter(COMBAT_PARAM_TYPE, COMBAT_HOLYDAMAGE) -- Define o tipo de dano (dano sagrado) | |
| 3 | + | combat:setParameter(COMBAT_PARAM_EFFECT, 127) -- Define o efeito visual do feitiço (ID 123) | |
| 4 | + | ||
| 5 | + | -- Fórmula para calcular o dano | |
| 6 | + | function onGetFormulaValues(player, level, magicLevel) | |
| 7 | + | -- Cálculo do dano mínimo: | |
| 8 | + | -- (level / 4): Dano que cresce com o nível do jogador | |
| 9 | + | -- (magicLevel * 4.6): Multiplicador do nível mágico com valor 4.6 | |
| 10 | + | -- + 8: Valor base mínimo | |
| 11 | + | local min = (level / 4) + (magicLevel * 4.6) + 8 | |
| 12 | + | ||
| 13 | + | -- Cálculo do dano máximo: | |
| 14 | + | -- (level / 4): Dano que cresce com o nível do jogador | |
| 15 | + | -- (magicLevel * 4.2): Multiplicador do nível mágico com valor 4.2 | |
| 16 | + | -- + 14: Valor base máximo | |
| 17 | + | local max = (level / 4) + (magicLevel * 4.2) + 14 | |
| 18 | + | ||
| 19 | + | return -min, -max -- Retorna os valores negativos (redução de HP) | |
| 20 | + | end | |
| 21 | + | ||
| 22 | + | combat:setCallback(CALLBACK_PARAM_LEVELMAGICVALUE, "onGetFormulaValues") -- Associa a função de dano ao combate | |
| 23 | + | ||
| 24 | + | -- Tabela com os efeitos visuais para cada direção | |
| 25 | + | local effects = { | |
| 26 | + | [NORTH] = 90, -- Efeito para o Norte (ID 90) | |
| 27 | + | [EAST] = 88, -- Efeito para o Leste (ID 88) | |
| 28 | + | [SOUTH] = 126, -- Efeito para o Sul (ID 124) | |
| 29 | + | [WEST] = 89 -- Efeito para o Oeste (ID 89) | |
| 30 | + | } | |
| 31 | + | ||
| 32 | + | local function applyDamage(creature, startPos, distance) | |
| 33 | + | local dir = creature:getDirection() -- Direção do atacante | |
| 34 | + | local currentPos = startPos -- Posição inicial do efeito | |
| 35 | + | local lastTarget = nil -- Armazena o último alvo que tomou dano | |
| 36 | + | ||
| 37 | + | for i = 0, distance - 1 do | |
| 38 | + | -- Cada passo do efeito é executado com um delay de i * 100ms | |
| 39 | + | addEvent(function() | |
| 40 | + | if not creature or creature:isRemoved() then return end | |
| 41 | + | ||
| 42 | + | -- Percorre os tiles adjacentes (offset de -1 a 1) para efeito de dano em área | |
| 43 | + | for offsetX = -1, 1 do | |
| 44 | + | local tile | |
| 45 | + | if dir == NORTH or dir == SOUTH then | |
| 46 | + | tile = Tile(Position(currentPos.x + offsetX, currentPos.y, currentPos.z)) | |
| 47 | + | else | |
| 48 | + | tile = Tile(Position(currentPos.x, currentPos.y + offsetX, currentPos.z)) | |
| 49 | + | end | |
| 50 | + | ||
| 51 | + | if tile then | |
| 52 | + | local target = tile:getTopCreature() -- Procura a criatura presente no tile | |
| 53 | + | if target and (target:isMonster() or target:isPlayer()) and target:getId() ~= creature:getId() then | |
| 54 | + | -- Ajusta o eixo x e y para o effect 123: | |
| 55 | + | local targetPos = target:getPosition() | |
| 56 | + | targetPos.x = targetPos.x + 0 -- ajuste no eixo x (modifique se necessário) | |
| 57 | + | targetPos.y = targetPos.y + 0 -- ajuste no eixo y (modifique se necessário) | |
| 58 | + | combat:execute(creature, Variant(targetPos)) -- Executa o ataque | |
| 59 | + | ||
| 60 | + | -- Cria a condição de paralisia para o alvo | |
| 61 | + | local paralysis = Condition(CONDITION_PARALYZE) | |
| 62 | + | paralysis:setParameter(CONDITION_PARAM_TICKS, 2000) -- Dura 2000ms (2 segundos) | |
| 63 | + | paralysis:setFormula(-0.9, 0, -0.9, 0) -- Parâmetros fixos da paralisia | |
| 64 | + | target:addCondition(paralysis) | |
| 65 | + | ||
| 66 | + | -- Envia o efeito visual (ID 85) 10 vezes, com intervalos de 300ms | |
| 67 | + | for j = 0, 9 do | |
| 68 | + | addEvent(function() | |
| 69 | + | if target and not target:isRemoved() then | |
| 70 | + | target:getPosition():sendMagicEffect(127) | |
| 71 | + | end | |
| 72 | + | end, j * 600) | |
| 73 | + | end | |
| 74 | + | ||
| 75 | + | lastTarget = target -- Atualiza o último alvo que tomou dano | |
| 76 | + | end | |
| 77 | + | end | |
| 78 | + | end | |
| 79 | + | ||
| 80 | + | -- Atualiza a posição para o próximo tile conforme a direção do atacante | |
| 81 | + | if dir == NORTH then | |
| 82 | + | currentPos.y = currentPos.y - 1 | |
| 83 | + | elseif dir == EAST then | |
| 84 | + | currentPos.x = currentPos.x + 1 | |
| 85 | + | elseif dir == SOUTH then | |
| 86 | + | currentPos.y = currentPos.y + 1 | |
| 87 | + | elseif dir == WEST then | |
| 88 | + | currentPos.x = currentPos.x - 1 | |
| 89 | + | end | |
| 90 | + | end, i * 100) -- Delay de 100ms entre cada passo | |
| 91 | + | end | |
| 92 | + | ||
| 93 | + | -- Após todos os passos, teleporta o último alvo atingido para frente do conjurador | |
| 94 | + | addEvent(function() | |
| 95 | + | if lastTarget and not lastTarget:isRemoved() and creature and not creature:isRemoved() then | |
| 96 | + | local casterPos = creature:getPosition() | |
| 97 | + | local teleportPos = Position(casterPos.x, casterPos.y, casterPos.z) | |
| 98 | + | if dir == NORTH then | |
| 99 | + | teleportPos.y = teleportPos.y - 1 | |
| 100 | + | elseif dir == EAST then | |
| 101 | + | teleportPos.x = teleportPos.x + 1 | |
| 102 | + | elseif dir == SOUTH then | |
| 103 | + | teleportPos.y = teleportPos.y + 1 | |
| 104 | + | elseif dir == WEST then | |
| 105 | + | teleportPos.x = teleportPos.x - 1 | |
| 106 | + | end | |
| 107 | + | lastTarget:teleportTo(teleportPos) | |
| 108 | + | teleportPos:sendMagicEffect(127) -- Efeito visual na nova posição do alvo | |
| 109 | + | end | |
| 110 | + | end, distance * 100 + 50) -- Executa após o último passo do efeito | |
| 111 | + | end | |
| 112 | + | ||
| 113 | + | local function showEffectInFront(creature) | |
| 114 | + | local dir = creature:getDirection() | |
| 115 | + | local pos = creature:getPosition() | |
| 116 | + | ||
| 117 | + | -- Define os offsets para posicionar o efeito visual "na frente" do personagem | |
| 118 | + | if dir == NORTH then | |
| 119 | + | pos.x = pos.x + 2 -- Avança 2 tiles no eixo x | |
| 120 | + | pos.y = pos.y - 1 -- Retrocede 1 tile no eixo y | |
| 121 | + | elseif dir == EAST then | |
| 122 | + | pos.x = pos.x + 6 -- Avança 6 tiles no eixo x | |
| 123 | + | pos.y = pos.y + 2 -- Avança 2 tiles no eixo y | |
| 124 | + | elseif dir == SOUTH then | |
| 125 | + | pos.x = pos.x + 0 -- Permanece no mesmo x | |
| 126 | + | pos.y = pos.y + 4 -- Avança 2 tiles no eixo y | |
| 127 | + | elseif dir == WEST then | |
| 128 | + | pos.x = pos.x - 1 -- Retrocede 1 tile no eixo x | |
| 129 | + | pos.y = pos.y + 2 -- Avança 2 tiles no eixo y | |
| 130 | + | end | |
| 131 | + | ||
| 132 | + | local effect = effects[dir] or CONST_ME_ENERGYAREA -- Seleciona o efeito conforme a direção ou usa padrão | |
| 133 | + | pos:sendMagicEffect(effect) -- Envia o efeito visual para a posição calculada | |
| 134 | + | end | |
| 135 | + | ||
| 136 | + | function onCastSpell(creature, var) | |
| 137 | + | local waittime = 1 -- Cooldown de 1 segundo entre os lançamentos da magia | |
| 138 | + | local storage = 99916 -- Chave de armazenamento para controle do cooldown | |
| 139 | + | ||
| 140 | + | if creature:getStorageValue(storage) > os.time() then | |
| 141 | + | creature:sendCancelMessage("Você só pode usar esta magia novamente em [" .. | |
| 142 | + | (creature:getStorageValue(storage) - os.time()) .. "] segundos.") | |
| 143 | + | return false | |
| 144 | + | end | |
| 145 | + | ||
| 146 | + | creature:setStorageValue(storage, os.time() + waittime) -- Atualiza o cooldown para o próximo uso | |
| 147 | + | ||
| 148 | + | local originalOutfit = creature:getOutfit() -- Guarda o visual original do personagem | |
| 149 | + | creature:getPosition():sendMagicEffect(127) -- Effect 320 no conjurador | |
| 150 | + | ||
| 151 | + | -- Define a sequência de outfits (lookType de 90 a 101) para a animação | |
| 152 | + | local outfits = { | |
| 153 | + | {lookType = 90}, -- Look inicial | |
| 154 | + | {lookType = 91}, -- Segundo visual | |
| 155 | + | {lookType = 92}, -- Terceiro visual | |
| 156 | + | {lookType = 93}, -- Quarto visual | |
| 157 | + | {lookType = 94}, -- Quinto visual | |
| 158 | + | {lookType = 95}, -- Sexto visual | |
| 159 | + | {lookType = 96}, -- Sétimo visual | |
| 160 | + | {lookType = 97}, -- Oitavo visual | |
| 161 | + | {lookType = 98}, -- Nono visual | |
| 162 | + | {lookType = 99}, -- Décimo visual | |
| 163 | + | {lookType = 100}, -- Décimo primeiro visual | |
| 164 | + | {lookType = 101}, -- Décimo segundo visual | |
| 165 | + | {lookType = 85} | |
| 166 | + | } | |
| 167 | + | ||
| 168 | + | -- Impede o movimento do jogador enquanto a magia é executada (paralisia temporária) | |
| 169 | + | local paralysis = Condition(CONDITION_PARALYZE) | |
| 170 | + | paralysis:setParameter(CONDITION_PARAM_TICKS, 900) -- Paralisia dura 900ms | |
| 171 | + | paralysis:setFormula(-1.0, 0, -1.0, 0) -- Parâmetros fixos da paralisia | |
| 172 | + | creature:addCondition(paralysis) | |
| 173 | + | ||
| 174 | + | -- Troca o outfit a cada 80ms para criar a animação | |
| 175 | + | for i = 1, #outfits do | |
| 176 | + | addEvent(function() | |
| 177 | + | if creature and not creature:isRemoved() then | |
| 178 | + | creature:setOutfit(outfits[i]) | |
| 179 | + | end | |
| 180 | + | end, (i - 1) * 80) | |
| 181 | + | end | |
| 182 | + | ||
| 183 | + | -- Aplica os efeitos visuais e o dano após 380ms | |
| 184 | + | addEvent(function() | |
| 185 | + | if not creature or creature:isRemoved() then return end | |
| 186 | + | ||
| 187 | + | local startPos = creature:getPosition() -- Posição de início do efeito | |
| 188 | + | local distance = 6 -- Distância que o efeito percorre (6 tiles) | |
| 189 | + | ||
| 190 | + | showEffectInFront(creature) -- Mostra o efeito na frente do personagem | |
| 191 | + | applyDamage(creature, startPos, distance) -- Aplica o dano e os efeitos aos alvos no caminho | |
| 192 | + | end, 380) | |
| 193 | + | ||
| 194 | + | -- Restaura o visual original do personagem após a sequência de animação | |
| 195 | + | addEvent(function() | |
| 196 | + | if creature and not creature:isRemoved() then | |
| 197 | + | creature:setOutfit(originalOutfit) | |
| 198 | + | end | |
| 199 | + | end, (#outfits * 100) + 300) -- Tempo total com base na sequência de outfits | |
| 200 | + | ||
| 201 | + | return false | |
| 202 | + | end |
| @@ -0,0 +1,58 @@ | |||
| 1 | + | local combat = createCombatObject() | |
| 2 | + | ||
| 3 | + | -- Configura�es do buff | |
| 4 | + | local buffDuration = 800 -- Dura��o total do buff (800 ms) | |
| 5 | + | local tickInterval = 200 -- Intervalo entre os ticks (200 ms) | |
| 6 | + | local ticks = 4 -- Quantidade de ticks | |
| 7 | + | local manaPercentPerTick = 0.10 -- 10% da mana m�xima por tick | |
| 8 | + | local baseHpPerTick = 100 -- Cura base por tick | |
| 9 | + | local levelScaling = 0.05 -- Aumento de 5% na cura a cada 10 n�veis | |
| 10 | + | ||
| 11 | + | -- Deslocamentos padr�es para outros efeitos | |
| 12 | + | local offsetX = 2 | |
| 13 | + | local offsetY = 0 | |
| 14 | + | ||
| 15 | + | -- Deslocamentos espec�ficos para o efeito 93 | |
| 16 | + | local offsetX93 = 0 | |
| 17 | + | local offsetY93 = 0 | |
| 18 | + | ||
| 19 | + | function onCastSpell(creature, var) | |
| 20 | + | local maxMana = creature:getMaxMana() | |
| 21 | + | local restorePerTick = math.floor(maxMana * manaPercentPerTick) | |
| 22 | + | local level = creature:getLevel() | |
| 23 | + | local tickCount = 0 | |
| 24 | + | ||
| 25 | + | local adjustedHpPerTick = math.floor(baseHpPerTick * (1 + math.floor(level / 10) * levelScaling)) | |
| 26 | + | ||
| 27 | + | local function restoreManaAndHp(creatureId) | |
| 28 | + | local creature = Creature(creatureId) | |
| 29 | + | if not creature then return end | |
| 30 | + | ||
| 31 | + | tickCount = tickCount + 1 | |
| 32 | + | creature:addMana(restorePerTick) | |
| 33 | + | creature:addHealth(adjustedHpPerTick) | |
| 34 | + | ||
| 35 | + | local playerPos = creature:getPosition() | |
| 36 | + | ||
| 37 | + | -- Aplica o efeito 93 com offsets separados | |
| 38 | + | local effectPos1 = Position(playerPos.x + offsetX93, playerPos.y + offsetY93, playerPos.z) | |
| 39 | + | effectPos1:sendMagicEffect(93) | |
| 40 | + | ||
| 41 | + | -- Aplica o efeito 125 apenas na primeira vez | |
| 42 | + | if tickCount == 1 then | |
| 43 | + | local effectPos2 = Position(playerPos.x + 2 - offsetX, playerPos.y - offsetY, playerPos.z) | |
| 44 | + | effectPos2:sendMagicEffect(125) | |
| 45 | + | end | |
| 46 | + | ||
| 47 | + | if tickCount < ticks then | |
| 48 | + | addEvent(restoreManaAndHp, tickInterval, creatureId) | |
| 49 | + | end | |
| 50 | + | end | |
| 51 | + | ||
| 52 | + | addEvent(restoreManaAndHp, tickInterval, creature:getId()) | |
| 53 | + | ||
| 54 | + | local adjustedPos = Position(creature:getPosition().x + offsetX, creature:getPosition().y + offsetY, creature:getPosition().z) | |
| 55 | + | adjustedPos:sendMagicEffect(100) | |
| 56 | + | ||
| 57 | + | return false | |
| 58 | + | end |
| @@ -0,0 +1,111 @@ | |||
| 1 | + | SPELL_ID = 00 | |
| 2 | + | local min = 0 | |
| 3 | + | local max = 0 | |
| 4 | + | ||
| 5 | + | -- =============== COMBAT VARS =============== | |
| 6 | + | -- Areas/Combat for 0ms | |
| 7 | + | local combat0_Brush = createCombatObject() | |
| 8 | + | setCombatParam(combat0_Brush, COMBAT_PARAM_EFFECT, CONST_ME_HITBYFIRE) | |
| 9 | + | setCombatParam(combat0_Brush, COMBAT_PARAM_TYPE, COMBAT_FIREDAMAGE) | |
| 10 | + | setCombatArea(combat0_Brush,createCombatArea({{1}, | |
| 11 | + | {2}, | |
| 12 | + | {1}})) | |
| 13 | + | function getDmg_Brush(cid, level, maglevel) | |
| 14 | + | ||
| 15 | + | return -min, -max | |
| 16 | + | end | |
| 17 | + | setCombatCallback(combat0_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush") | |
| 18 | + | ||
| 19 | + | -- Areas/Combat for 300ms | |
| 20 | + | local combat3_Brush = createCombatObject() | |
| 21 | + | setCombatParam(combat3_Brush, COMBAT_PARAM_EFFECT, CONST_ME_HITBYFIRE) | |
| 22 | + | setCombatParam(combat3_Brush, COMBAT_PARAM_TYPE, COMBAT_FIREDAMAGE) | |
| 23 | + | setCombatArea(combat3_Brush,createCombatArea({{1, 2, 1}})) | |
| 24 | + | function getDmg_Brush(cid, level, maglevel) | |
| 25 | + | ||
| 26 | + | return -min, -max | |
| 27 | + | end | |
| 28 | + | setCombatCallback(combat3_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush") | |
| 29 | + | ||
| 30 | + | -- Areas/Combat for 600ms | |
| 31 | + | local combat6_Brush = createCombatObject() | |
| 32 | + | setCombatParam(combat6_Brush, COMBAT_PARAM_EFFECT, CONST_ME_HITBYFIRE) | |
| 33 | + | setCombatParam(combat6_Brush, COMBAT_PARAM_TYPE, COMBAT_FIREDAMAGE) | |
| 34 | + | setCombatArea(combat6_Brush,createCombatArea({{1, 0, 0}, | |
| 35 | + | {0, 2, 0}, | |
| 36 | + | {0, 0, 1}})) | |
| 37 | + | function getDmg_Brush(cid, level, maglevel) | |
| 38 | + | ||
| 39 | + | return -min, -max | |
| 40 | + | end | |
| 41 | + | setCombatCallback(combat6_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush") | |
| 42 | + | ||
| 43 | + | -- Areas/Combat for 900ms | |
| 44 | + | local combat9_Brush = createCombatObject() | |
| 45 | + | setCombatParam(combat9_Brush, COMBAT_PARAM_EFFECT, CONST_ME_HITBYFIRE) | |
| 46 | + | setCombatParam(combat9_Brush, COMBAT_PARAM_TYPE, COMBAT_FIREDAMAGE) | |
| 47 | + | setCombatArea(combat9_Brush,createCombatArea({{0, 0, 1}, | |
| 48 | + | {0, 2, 0}, | |
| 49 | + | {1, 0, 0}})) | |
| 50 | + | function getDmg_Brush(cid, level, maglevel) | |
| 51 | + | ||
| 52 | + | return -min, -max | |
| 53 | + | end | |
| 54 | + | setCombatCallback(combat9_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush") | |
| 55 | + | ||
| 56 | + | -- =============== CORE FUNCTIONS =============== | |
| 57 | + | local function RunPart(c,cid,var,dirList,dirEmitPos) -- Part | |
| 58 | + | if (isCreature(cid)) then | |
| 59 | + | doCombat(cid, c, var) | |
| 60 | + | if (dirList ~= nil) then -- Emit distance effects | |
| 61 | + | local i = 2; | |
| 62 | + | while (i < #dirList) do | |
| 63 | + | doSendDistanceShoot(dirEmitPos,{x=dirEmitPos.x-dirList[i],y=dirEmitPos.y-dirList[i+1],z=dirEmitPos.z},dirList[1]) | |
| 64 | + | i = i + 2 | |
| 65 | + | end | |
| 66 | + | end | |
| 67 | + | end | |
| 68 | + | end | |
| 69 | + | function checkSpell20(cid) | |
| 70 | + | local GUN_ID = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_01) | |
| 71 | + | local CHECK_SLOT_01 = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_04) | |
| 72 | + | local CHECK_SLOT_02 = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_05) | |
| 73 | + | local CHECK_SLOT_03 = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_06) | |
| 74 | + | SPELL_ID = 20 | |
| 75 | + | ||
| 76 | + | if GUN_ID > 0 then | |
| 77 | + | if CHECK_SLOT_01 == SPELL_ID then | |
| 78 | + | cid:sendCancelMessage("@SpellCooldown 01") | |
| 79 | + | return true | |
| 80 | + | elseif CHECK_SLOT_02 == SPELL_ID then | |
| 81 | + | cid:sendCancelMessage("@SpellCooldown 02") | |
| 82 | + | return true | |
| 83 | + | elseif CHECK_SLOT_03 == SPELL_ID then | |
| 84 | + | cid:sendCancelMessage("@SpellCooldown 03") | |
| 85 | + | return true | |
| 86 | + | else | |
| 87 | + | return false | |
| 88 | + | end | |
| 89 | + | else | |
| 90 | + | return false | |
| 91 | + | end | |
| 92 | + | return true | |
| 93 | + | end | |
| 94 | + | function onCastSpell(cid, var) | |
| 95 | + | if checkSpell20(cid) or cid:getGroup():getAccess() then | |
| 96 | + | local startPos = getCreaturePosition(cid) | |
| 97 | + | local GUN_ID = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_01) | |
| 98 | + | local starGun = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_03) | |
| 99 | + | local levelGun = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_07) | |
| 100 | + | min = onDamage(cid, GUN_ID, levelGun, starGun, "SKILL_MIN", SPELL_ID) | |
| 101 | + | max = min | |
| 102 | + | RunPart(combat0_Brush,cid,var) | |
| 103 | + | addEvent(RunPart,300,combat3_Brush,cid.uid,var) | |
| 104 | + | addEvent(RunPart,600,combat6_Brush,cid.uid,var) | |
| 105 | + | addEvent(RunPart,900,combat9_Brush,cid.uid,var) | |
| 106 | + | return true | |
| 107 | + | else | |
| 108 | + | cid:getPosition():sendMagicEffect(03) | |
| 109 | + | return false | |
| 110 | + | end | |
| 111 | + | end |
| @@ -0,0 +1,107 @@ | |||
| 1 | + | SPELL_ID = 00 | |
| 2 | + | local min = 0 | |
| 3 | + | local max = 0 | |
| 4 | + | ||
| 5 | + | -- =============== COMBAT VARS =============== | |
| 6 | + | -- Areas/Combat for 0ms | |
| 7 | + | local combat0_Brush = createCombatObject() | |
| 8 | + | setCombatParam(combat0_Brush, COMBAT_PARAM_EFFECT, CONST_ME_ICEATTACK) | |
| 9 | + | setCombatParam(combat0_Brush, COMBAT_PARAM_TYPE, COMBAT_ICEDAMAGE) | |
| 10 | + | setCombatArea(combat0_Brush,createCombatArea({{2}})) | |
| 11 | + | function getDmg_Brush(cid, level, maglevel) | |
| 12 | + | ||
| 13 | + | return -min, -max | |
| 14 | + | end | |
| 15 | + | setCombatCallback(combat0_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush")local combat0_Brush = createCombatObject() | |
| 16 | + | setCombatParam(combat0_Brush, COMBAT_PARAM_EFFECT, CONST_ME_ICEATTACK) | |
| 17 | + | setCombatParam(combat0_Brush, COMBAT_PARAM_DISTANCEEFFECT, CONST_ANI_ICE) | |
| 18 | + | setCombatParam(combat0_Brush, COMBAT_PARAM_TYPE, COMBAT_ICEDAMAGE) | |
| 19 | + | setCombatArea(combat0_Brush,createCombatArea({{3}})) | |
| 20 | + | function getDmg_Brush(cid, level, maglevel) | |
| 21 | + | ||
| 22 | + | return -min, -max | |
| 23 | + | end | |
| 24 | + | setCombatCallback(combat0_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush") | |
| 25 | + | ||
| 26 | + | -- Areas/Combat for 100ms | |
| 27 | + | local combat1_Brush = createCombatObject() | |
| 28 | + | setCombatParam(combat1_Brush, COMBAT_PARAM_EFFECT, CONST_ME_ICEATTACK) | |
| 29 | + | setCombatParam(combat1_Brush, COMBAT_PARAM_DISTANCEEFFECT, CONST_ANI_ICE) | |
| 30 | + | setCombatParam(combat1_Brush, COMBAT_PARAM_TYPE, COMBAT_ICEDAMAGE) | |
| 31 | + | setCombatArea(combat1_Brush,createCombatArea({{3}})) | |
| 32 | + | function getDmg_Brush(cid, level, maglevel) | |
| 33 | + | ||
| 34 | + | return -min, -max | |
| 35 | + | end | |
| 36 | + | setCombatCallback(combat1_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush") | |
| 37 | + | ||
| 38 | + | -- Areas/Combat for 200ms | |
| 39 | + | local combat2_Brush = createCombatObject() | |
| 40 | + | setCombatParam(combat2_Brush, COMBAT_PARAM_EFFECT, CONST_ME_ICEATTACK) | |
| 41 | + | setCombatParam(combat2_Brush, COMBAT_PARAM_DISTANCEEFFECT, CONST_ANI_ICE) | |
| 42 | + | setCombatParam(combat2_Brush, COMBAT_PARAM_TYPE, COMBAT_ICEDAMAGE) | |
| 43 | + | setCombatArea(combat2_Brush,createCombatArea({{3}})) | |
| 44 | + | function getDmg_Brush(cid, level, maglevel) | |
| 45 | + | ||
| 46 | + | return -min, -max | |
| 47 | + | end | |
| 48 | + | setCombatCallback(combat2_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush") | |
| 49 | + | ||
| 50 | + | -- =============== CORE FUNCTIONS =============== | |
| 51 | + | local function RunPart(c,cid,var,dirList,dirEmitPos) -- Part | |
| 52 | + | if (isCreature(cid)) then | |
| 53 | + | doCombat(cid, c, var) | |
| 54 | + | if (dirList ~= nil) then -- Emit distance effects | |
| 55 | + | local i = 2; | |
| 56 | + | while (i < #dirList) do | |
| 57 | + | doSendDistanceShoot(dirEmitPos,{x=dirEmitPos.x-dirList[i],y=dirEmitPos.y-dirList[i+1],z=dirEmitPos.z},dirList[1]) | |
| 58 | + | i = i + 2 | |
| 59 | + | end | |
| 60 | + | end | |
| 61 | + | end | |
| 62 | + | end | |
| 63 | + | ||
| 64 | + | function checkSpell3(cid) | |
| 65 | + | local GUN_ID = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_01) | |
| 66 | + | local CHECK_SLOT_01 = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_04) | |
| 67 | + | local CHECK_SLOT_02 = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_05) | |
| 68 | + | local CHECK_SLOT_03 = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_06) | |
| 69 | + | SPELL_ID = 03 | |
| 70 | + | ||
| 71 | + | if GUN_ID > 0 then | |
| 72 | + | if CHECK_SLOT_01 == SPELL_ID then | |
| 73 | + | cid:sendCancelMessage("@SpellCooldown 01") | |
| 74 | + | return true | |
| 75 | + | elseif CHECK_SLOT_02 == SPELL_ID then | |
| 76 | + | cid:sendCancelMessage("@SpellCooldown 02") | |
| 77 | + | return true | |
| 78 | + | elseif CHECK_SLOT_03 == SPELL_ID then | |
| 79 | + | cid:sendCancelMessage("@SpellCooldown 03") | |
| 80 | + | return true | |
| 81 | + | else | |
| 82 | + | return false | |
| 83 | + | end | |
| 84 | + | else | |
| 85 | + | return false | |
| 86 | + | end | |
| 87 | + | return true | |
| 88 | + | end | |
| 89 | + | ||
| 90 | + | function onCastSpell(cid, var) | |
| 91 | + | if checkSpell3(cid) or cid:getGroup():getAccess() then | |
| 92 | + | local startPos = getCreaturePosition(cid) | |
| 93 | + | local GUN_ID = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_01) | |
| 94 | + | local starGun = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_03) | |
| 95 | + | local levelGun = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_07) | |
| 96 | + | min = onDamage(cid, GUN_ID, levelGun, starGun, "SKILL_MIN", SPELL_ID) | |
| 97 | + | max = min | |
| 98 | + | RunPart(combat0_Brush,cid,var) | |
| 99 | + | RunPart(combat0_Brush,cid,var) | |
| 100 | + | addEvent(RunPart,300,combat1_Brush,cid.uid,var) | |
| 101 | + | addEvent(RunPart,600,combat2_Brush,cid.uid,var) | |
| 102 | + | return true | |
| 103 | + | else | |
| 104 | + | cid:getPosition():sendMagicEffect(03) | |
| 105 | + | return false | |
| 106 | + | end | |
| 107 | + | end |
| @@ -0,0 +1,109 @@ | |||
| 1 | + | function onCastSpell(creature, var) | |
| 2 | + | local COOLDOWN = { | |
| 3 | + | [-1] = 360; | |
| 4 | + | [00] = 360; | |
| 5 | + | [01] = 300; | |
| 6 | + | [02] = 240; | |
| 7 | + | [03] = 180; | |
| 8 | + | [04] = 120; | |
| 9 | + | } | |
| 10 | + | -- MAESTRIA: REGEN | |
| 11 | + | if creature:getStorageValue(_SYSTEM.MAESTRIA[01]) == 01 then | |
| 12 | + | if creature:getStorageValue(_SYSTEM.MAESTRIA[03]) > 0 then | |
| 13 | + | creature:getPosition():sendMagicEffect(CONST_ME_POFF) | |
| 14 | + | return true | |
| 15 | + | end | |
| 16 | + | ||
| 17 | + | local WaitTime = COOLDOWN[creature:getStorageValue(_SYSTEM.MAESTRIA[02])] | |
| 18 | + | creature:setStorageValue(_SYSTEM.MAESTRIA[04], 60) | |
| 19 | + | creature:setStorageValue(_SYSTEM.MAESTRIA[03], WaitTime + 3) | |
| 20 | + | ||
| 21 | + | creature:getPosition():sendMagicEffect(CONST_ME_MAGIC_GREEN) | |
| 22 | + | creature:sendCancelMessage("@SpellCooldown 06 " ..WaitTime) | |
| 23 | + | ||
| 24 | + | local regenCondition = Condition(CONDITION_REGENERATION, CONDITIONID_DEFAULT) | |
| 25 | + | local RegenRandom = (math.random(05, 10)) | |
| 26 | + | local HPGain = RegenRandom * (creature:getBaseMaxHealth() / 100) | |
| 27 | + | ||
| 28 | + | regenCondition:setTicks(01 * 60 * 1000) | |
| 29 | + | regenCondition:setParameter(CONDITION_PARAM_BUFF_SPELL, true) | |
| 30 | + | regenCondition:setParameter(CONDITION_PARAM_HEALTHTICKS, 1000) | |
| 31 | + | regenCondition:setParameter(CONDITION_PARAM_HEALTHGAIN, HPGain) | |
| 32 | + | creature:addCondition(regenCondition) | |
| 33 | + | ||
| 34 | + | -- MAESTRIA: TANKER | |
| 35 | + | elseif creature:getStorageValue(_SYSTEM.MAESTRIA[01]) == 02 then | |
| 36 | + | if creature:getStorageValue(_SYSTEM.MAESTRIA[03]) > 0 then | |
| 37 | + | creature:getPosition():sendMagicEffect(CONST_ME_POFF) | |
| 38 | + | return true | |
| 39 | + | end | |
| 40 | + | ||
| 41 | + | local WaitTime = COOLDOWN[creature:getStorageValue(_SYSTEM.MAESTRIA[02])] | |
| 42 | + | creature:setStorageValue(_SYSTEM.MAESTRIA[04], 10) | |
| 43 | + | creature:setStorageValue(_SYSTEM.MAESTRIA[03], WaitTime + 3) | |
| 44 | + | ||
| 45 | + | creature:getPosition():sendMagicEffect(CONST_ME_MAGIC_GREEN) | |
| 46 | + | creature:sendCancelMessage("@SpellCooldown 06 " ..WaitTime) | |
| 47 | + | ||
| 48 | + | -- MAESTRIA: SHOOTER | |
| 49 | + | elseif creature:getStorageValue(_SYSTEM.MAESTRIA[01]) == 03 then | |
| 50 | + | if creature:getStorageValue(_SYSTEM.MAESTRIA[03]) > 0 then | |
| 51 | + | creature:getPosition():sendMagicEffect(CONST_ME_POFF) | |
| 52 | + | return true | |
| 53 | + | end | |
| 54 | + | ||
| 55 | + | local WaitTime = COOLDOWN[creature:getStorageValue(_SYSTEM.MAESTRIA[02])] | |
| 56 | + | creature:setStorageValue(_SYSTEM.MAESTRIA[04], 10) | |
| 57 | + | creature:setStorageValue(_SYSTEM.MAESTRIA[03], WaitTime + 3) | |
| 58 | + | ||
| 59 | + | creature:getPosition():sendMagicEffect(CONST_ME_MAGIC_GREEN) | |
| 60 | + | creature:sendCancelMessage("@SpellCooldown 06 " ..WaitTime) | |
| 61 | + | ||
| 62 | + | -- MAESTRIA: VITAL | |
| 63 | + | elseif creature:getStorageValue(_SYSTEM.MAESTRIA[01]) == 04 then | |
| 64 | + | if creature:getStorageValue(_SYSTEM.MAESTRIA[03]) > 0 then | |
| 65 | + | creature:getPosition():sendMagicEffect(CONST_ME_POFF) | |
| 66 | + | return true | |
| 67 | + | end | |
| 68 | + | ||
| 69 | + | local WaitTime = COOLDOWN[creature:getStorageValue(_SYSTEM.MAESTRIA[02])] | |
| 70 | + | creature:setStorageValue(_SYSTEM.MAESTRIA[04], 10) | |
| 71 | + | creature:setStorageValue(_SYSTEM.MAESTRIA[03], WaitTime + 3) | |
| 72 | + | ||
| 73 | + | creature:getPosition():sendMagicEffect(CONST_ME_MAGIC_GREEN) | |
| 74 | + | creature:sendCancelMessage("@SpellCooldown 06 " ..WaitTime) | |
| 75 | + | ||
| 76 | + | local gainedHealth = creature:getBaseMaxHealth() | |
| 77 | + | local condition = Condition(CONDITION_ATTRIBUTES) | |
| 78 | + | condition:setParameter(CONDITION_PARAM_STAT_MAXHITPOINTS, gainedHealth) | |
| 79 | + | condition:setParameter(CONDITION_PARAM_BUFF_SPELL, true) | |
| 80 | + | condition:setParameter(CONDITION_PARAM_TICKS, 10 * 1000) | |
| 81 | + | creature:addCondition(condition) | |
| 82 | + | ||
| 83 | + | doTargetCombat(0, creature, COMBAT_HEALING, gainedHealth * 10, gainedHealth * 10) | |
| 84 | + | ||
| 85 | + | -- MAESTRIA: LUCKY | |
| 86 | + | elseif creature:getStorageValue(_SYSTEM.MAESTRIA[01]) == 05 then | |
| 87 | + | if creature:getStorageValue(_SYSTEM.MAESTRIA[03]) > 0 then | |
| 88 | + | creature:getPosition():sendMagicEffect(CONST_ME_POFF) | |
| 89 | + | return true | |
| 90 | + | end | |
| 91 | + | ||
| 92 | + | local WaitTime = COOLDOWN[creature:getStorageValue(_SYSTEM.MAESTRIA[02])] | |
| 93 | + | creature:setStorageValue(_SYSTEM.MAESTRIA[04], 60) | |
| 94 | + | creature:setStorageValue(_SYSTEM.MAESTRIA[03], WaitTime + 3) | |
| 95 | + | ||
| 96 | + | creature:getPosition():sendMagicEffect(CONST_ME_MAGIC_GREEN) | |
| 97 | + | creature:sendCancelMessage("@SpellCooldown 06 " ..WaitTime) | |
| 98 | + | ||
| 99 | + | else | |
| 100 | + | creature:getPosition():sendMagicEffect(CONST_ME_POFF) | |
| 101 | + | return true | |
| 102 | + | end | |
| 103 | + | ||
| 104 | + | -- DESAFIO | |
| 105 | + | if creature:getStorageValue(_DESAFIOS[00].DESAFIO_ID) > 00 then | |
| 106 | + | onPlayerDesafios(creature, 30, 01) | |
| 107 | + | end | |
| 108 | + | return true | |
| 109 | + | end |
| @@ -0,0 +1,195 @@ | |||
| 1 | + | SPELL_ID = 00 | |
| 2 | + | local min = 0 | |
| 3 | + | local max = 0 | |
| 4 | + | ||
| 5 | + | -- =============== COMBAT VARS =============== | |
| 6 | + | -- Areas/Combat for 100ms | |
| 7 | + | local combat1_Brush = createCombatObject() | |
| 8 | + | setCombatParam(combat1_Brush, COMBAT_PARAM_EFFECT, CONST_ME_BIGCLOUDS) | |
| 9 | + | setCombatParam(combat1_Brush, COMBAT_PARAM_TYPE, COMBAT_HOLYDAMAGE) | |
| 10 | + | setCombatArea(combat1_Brush,createCombatArea({{0, 0, 0, 0, 0, 1}, | |
| 11 | + | {1, 0, 0, 0, 0, 0}, | |
| 12 | + | {0, 0, 2, 1, 0, 0}, | |
| 13 | + | {0, 0, 0, 0, 0, 0}, | |
| 14 | + | {0, 0, 0, 0, 0, 0}, | |
| 15 | + | {0, 0, 1, 0, 0, 0}})) | |
| 16 | + | function getDmg_Brush(cid, level, maglevel) | |
| 17 | + | ||
| 18 | + | return -min, -max | |
| 19 | + | end | |
| 20 | + | setCombatCallback(combat1_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush")local combat1_Brush_2 = createCombatObject() | |
| 21 | + | setCombatParam(combat1_Brush_2, COMBAT_PARAM_EFFECT, CONST_ME_YELLOWENERGY) | |
| 22 | + | setCombatParam(combat1_Brush_2, COMBAT_PARAM_TYPE, COMBAT_HOLYDAMAGE) | |
| 23 | + | setCombatArea(combat1_Brush_2,createCombatArea({{0, 1, 0, 0, 1, 0, 0}, | |
| 24 | + | {0, 0, 0, 0, 1, 0, 0}, | |
| 25 | + | {0, 0, 0, 2, 0, 0, 1}, | |
| 26 | + | {0, 1, 0, 1, 1, 0, 0}, | |
| 27 | + | {1, 0, 0, 0, 0, 0, 1}, | |
| 28 | + | {0, 0, 1, 0, 0, 1, 0}})) | |
| 29 | + | function getDmg_Brush_2(cid, level, maglevel) | |
| 30 | + | ||
| 31 | + | return -min, -max | |
| 32 | + | end | |
| 33 | + | setCombatCallback(combat1_Brush_2, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush_2") | |
| 34 | + | ||
| 35 | + | -- Areas/Combat for 0ms | |
| 36 | + | local combat0_Brush = createCombatObject() | |
| 37 | + | setCombatParam(combat0_Brush, COMBAT_PARAM_EFFECT, CONST_ME_BIGCLOUDS) | |
| 38 | + | setCombatParam(combat0_Brush, COMBAT_PARAM_TYPE, COMBAT_HOLYDAMAGE) | |
| 39 | + | setCombatArea(combat0_Brush,createCombatArea({{0, 0, 0, 1, 0, 0}, | |
| 40 | + | {0, 0, 0, 0, 0, 0}, | |
| 41 | + | {1, 0, 0, 2, 0, 0}, | |
| 42 | + | {0, 0, 0, 0, 0, 0}, | |
| 43 | + | {0, 1, 0, 0, 0, 1}})) | |
| 44 | + | function getDmg_Brush(cid, level, maglevel) | |
| 45 | + | ||
| 46 | + | return -min, -max | |
| 47 | + | end | |
| 48 | + | setCombatCallback(combat0_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush") | |
| 49 | + | ||
| 50 | + | -- Areas/Combat for 200ms | |
| 51 | + | local combat2_Brush = createCombatObject() | |
| 52 | + | setCombatParam(combat2_Brush, COMBAT_PARAM_EFFECT, CONST_ME_BIGCLOUDS) | |
| 53 | + | setCombatParam(combat2_Brush, COMBAT_PARAM_TYPE, COMBAT_HOLYDAMAGE) | |
| 54 | + | setCombatArea(combat2_Brush,createCombatArea({{0, 0, 0, 0, 0, 1, 0}, | |
| 55 | + | {0, 0, 0, 2, 0, 0, 0}, | |
| 56 | + | {0, 0, 1, 0, 0, 0, 1}, | |
| 57 | + | {0, 0, 0, 0, 0, 0, 0}, | |
| 58 | + | {1, 0, 0, 0, 0, 0, 0}})) | |
| 59 | + | function getDmg_Brush(cid, level, maglevel) | |
| 60 | + | ||
| 61 | + | return -min, -max | |
| 62 | + | end | |
| 63 | + | setCombatCallback(combat2_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush")local combat2_Brush_2 = createCombatObject() | |
| 64 | + | setCombatParam(combat2_Brush_2, COMBAT_PARAM_EFFECT, CONST_ME_YELLOWENERGY) | |
| 65 | + | setCombatParam(combat2_Brush_2, COMBAT_PARAM_TYPE, COMBAT_HOLYDAMAGE) | |
| 66 | + | setCombatArea(combat2_Brush_2,createCombatArea({{1, 0, 0, 0}, | |
| 67 | + | {0, 2, 0, 0}, | |
| 68 | + | {0, 0, 0, 1}, | |
| 69 | + | {1, 0, 1, 0}, | |
| 70 | + | {0, 0, 1, 0}})) | |
| 71 | + | function getDmg_Brush_2(cid, level, maglevel) | |
| 72 | + | ||
| 73 | + | return -min, -max | |
| 74 | + | end | |
| 75 | + | setCombatCallback(combat2_Brush_2, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush_2") | |
| 76 | + | ||
| 77 | + | -- Areas/Combat for 300ms | |
| 78 | + | local combat3_Brush = createCombatObject() | |
| 79 | + | setCombatParam(combat3_Brush, COMBAT_PARAM_EFFECT, CONST_ME_BIGCLOUDS) | |
| 80 | + | setCombatParam(combat3_Brush, COMBAT_PARAM_TYPE, COMBAT_HOLYDAMAGE) | |
| 81 | + | setCombatArea(combat3_Brush,createCombatArea({{1, 1, 0, 0, 0, 0, 0}, | |
| 82 | + | {0, 0, 0, 0, 0, 0, 0}, | |
| 83 | + | {0, 0, 0, 2, 0, 0, 0}, | |
| 84 | + | {0, 0, 0, 0, 0, 0, 0}, | |
| 85 | + | {0, 0, 0, 1, 0, 0, 0}, | |
| 86 | + | {0, 0, 0, 0, 0, 0, 1}})) | |
| 87 | + | function getDmg_Brush(cid, level, maglevel) | |
| 88 | + | ||
| 89 | + | return -min, -max | |
| 90 | + | end | |
| 91 | + | setCombatCallback(combat3_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush")local combat3_Brush_2 = createCombatObject() | |
| 92 | + | setCombatParam(combat3_Brush_2, COMBAT_PARAM_EFFECT, CONST_ME_YELLOWENERGY) | |
| 93 | + | setCombatParam(combat3_Brush_2, COMBAT_PARAM_TYPE, COMBAT_HOLYDAMAGE) | |
| 94 | + | setCombatArea(combat3_Brush_2,createCombatArea({{0, 0, 1, 0, 0, 1}, | |
| 95 | + | {1, 0, 2, 0, 1, 0}, | |
| 96 | + | {0, 0, 0, 0, 0, 0}, | |
| 97 | + | {0, 0, 0, 0, 0, 0}, | |
| 98 | + | {1, 0, 0, 0, 0, 0}})) | |
| 99 | + | function getDmg_Brush_2(cid, level, maglevel) | |
| 100 | + | ||
| 101 | + | return -min, -max | |
| 102 | + | end | |
| 103 | + | setCombatCallback(combat3_Brush_2, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush_2") | |
| 104 | + | ||
| 105 | + | -- Areas/Combat for 400ms | |
| 106 | + | local combat4_Brush = createCombatObject() | |
| 107 | + | setCombatParam(combat4_Brush, COMBAT_PARAM_EFFECT, CONST_ME_BIGCLOUDS) | |
| 108 | + | setCombatParam(combat4_Brush, COMBAT_PARAM_TYPE, COMBAT_HOLYDAMAGE) | |
| 109 | + | setCombatArea(combat4_Brush,createCombatArea({{0, 0, 0, 1}, | |
| 110 | + | {0, 0, 0, 0}, | |
| 111 | + | {1, 2, 0, 0}, | |
| 112 | + | {0, 0, 1, 0}, | |
| 113 | + | {0, 0, 0, 0}, | |
| 114 | + | {0, 0, 1, 0}})) | |
| 115 | + | function getDmg_Brush(cid, level, maglevel) | |
| 116 | + | ||
| 117 | + | return -min, -max | |
| 118 | + | end | |
| 119 | + | setCombatCallback(combat4_Brush, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush")local combat4_Brush_2 = createCombatObject() | |
| 120 | + | setCombatParam(combat4_Brush_2, COMBAT_PARAM_EFFECT, CONST_ME_YELLOWENERGY) | |
| 121 | + | setCombatParam(combat4_Brush_2, COMBAT_PARAM_TYPE, COMBAT_HOLYDAMAGE) | |
| 122 | + | setCombatArea(combat4_Brush_2,createCombatArea({{0, 0, 0, 0, 1, 0, 0, 0, 0}, | |
| 123 | + | {0, 0, 0, 1, 0, 0, 0, 0, 0}, | |
| 124 | + | {0, 1, 0, 0, 0, 0, 0, 0, 0}, | |
| 125 | + | {1, 0, 0, 0, 2, 0, 0, 0, 1}, | |
| 126 | + | {0, 1, 0, 0, 0, 0, 0, 0, 0}, | |
| 127 | + | {0, 0, 0, 0, 0, 0, 0, 0, 0}, | |
| 128 | + | {0, 0, 0, 0, 1, 0, 0, 0, 0}, | |
| 129 | + | {0, 0, 0, 0, 1, 0, 0, 0, 0}})) | |
| 130 | + | function getDmg_Brush_2(cid, level, maglevel) | |
| 131 | + | ||
| 132 | + | return -min, -max | |
| 133 | + | end | |
| 134 | + | setCombatCallback(combat4_Brush_2, CALLBACK_PARAM_LEVELMAGICVALUE, "getDmg_Brush_2") | |
| 135 | + | ||
| 136 | + | -- =============== CORE FUNCTIONS =============== | |
| 137 | + | local function RunPart(c,cid,var,dirList,dirEmitPos) -- Part | |
| 138 | + | if (isCreature(cid)) then | |
| 139 | + | doCombat(cid, c, var) | |
| 140 | + | if (dirList ~= nil) then -- Emit distance effects | |
| 141 | + | local i = 2; | |
| 142 | + | while (i < #dirList) do | |
| 143 | + | doSendDistanceShoot(dirEmitPos,{x=dirEmitPos.x-dirList[i],y=dirEmitPos.y-dirList[i+1],z=dirEmitPos.z},dirList[1]) | |
| 144 | + | i = i + 2 | |
| 145 | + | end | |
| 146 | + | end | |
| 147 | + | end | |
| 148 | + | end | |
| 149 | + | function checkSpell49(cid) | |
| 150 | + | local GUN_ID = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_01) | |
| 151 | + | local CHECK_SLOT_01 = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_04) | |
| 152 | + | local CHECK_SLOT_02 = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_05) | |
| 153 | + | local CHECK_SLOT_03 = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_06) | |
| 154 | + | SPELL_ID = 49 | |
| 155 | + | ||
| 156 | + | if GUN_ID > 0 then | |
| 157 | + | if CHECK_SLOT_01 == SPELL_ID then | |
| 158 | + | cid:sendCancelMessage("@SpellCooldown 01") | |
| 159 | + | return true | |
| 160 | + | elseif CHECK_SLOT_02 == SPELL_ID then | |
| 161 | + | cid:sendCancelMessage("@SpellCooldown 02") | |
| 162 | + | return true | |
| 163 | + | elseif CHECK_SLOT_03 == SPELL_ID then | |
| 164 | + | cid:sendCancelMessage("@SpellCooldown 03") | |
| 165 | + | return true | |
| 166 | + | else | |
| 167 | + | return false | |
| 168 | + | end | |
| 169 | + | else | |
| 170 | + | return false | |
| 171 | + | end | |
| 172 | + | end | |
| 173 | + | function onCastSpell(cid, var) | |
| 174 | + | if checkSpell49(cid) or cid:getGroup():getAccess() then | |
| 175 | + | local startPos = getCreaturePosition(cid) | |
| 176 | + | local GUN_ID = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_01) | |
| 177 | + | local starGun = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_03) | |
| 178 | + | local levelGun = cid:getStorageValue(_SYSTEM.INVENTARIO[04].UID_07) | |
| 179 | + | min = onDamage(cid, GUN_ID, levelGun, starGun, "SKILL_MIN", SPELL_ID) | |
| 180 | + | max = min | |
| 181 | + | addEvent(RunPart,100,combat1_Brush,cid.uid,var) | |
| 182 | + | addEvent(RunPart,100,combat1_Brush_2,cid.uid,var) | |
| 183 | + | RunPart(combat0_Brush,cid,var) | |
| 184 | + | addEvent(RunPart,200,combat2_Brush,cid.uid,var) | |
| 185 | + | addEvent(RunPart,200,combat2_Brush_2,cid.uid,var) | |
| 186 | + | addEvent(RunPart,300,combat3_Brush,cid.uid,var) | |
| 187 | + | addEvent(RunPart,300,combat3_Brush_2,cid.uid,var) | |
| 188 | + | addEvent(RunPart,400,combat4_Brush,cid.uid,var) | |
| 189 | + | addEvent(RunPart,400,combat4_Brush_2,cid.uid,var) | |
| 190 | + | return true | |
| 191 | + | else | |
| 192 | + | cid:getPosition():sendMagicEffect(03) | |
| 193 | + | return false | |
| 194 | + | end | |
| 195 | + | end |
| @@ -0,0 +1,23 @@ | |||
| 1 | + | local combat = Combat() | |
| 2 | + | combat:setParameter(COMBAT_PARAM_DISTANCEEFFECT, CONST_ANI_SNOWBALL) | |
| 3 | + | combat:setParameter(COMBAT_PARAM_EFFECT, CONST_ME_POFF) | |
| 4 | + | ||
| 5 | + | local parameters = { | |
| 6 | + | {key = CONDITION_PARAM_TICKS, value = 5 * 1000}, | |
| 7 | + | {key = CONDITION_PARAM_SKILL_FIST, value = nil}, | |
| 8 | + | {key = CONDITION_PARAM_SKILL_CLUB, value = nil}, | |
| 9 | + | {key = CONDITION_PARAM_SKILL_SWORD, value = nil}, | |
| 10 | + | {key = CONDITION_PARAM_SKILL_AXE, value = nil}, | |
| 11 | + | {key = CONDITION_PARAM_SKILL_DISTANCE, value = nil}, | |
| 12 | + | {key = CONDITION_PARAM_SKILL_SHIELD, value = nil} | |
| 13 | + | } | |
| 14 | + | ||
| 15 | + | function onCastSpell(creature, variant) | |
| 16 | + | local index = math.random(2, #parameters) | |
| 17 | + | parameters[index].value = -math.random(1, 6) | |
| 18 | + | ||
| 19 | + | for _, target in ipairs(combat:getTargets(creature, variant)) do | |
| 20 | + | target:addAttributeCondition({parameters[1], parameters[index]}) | |
| 21 | + | end | |
| 22 | + | return true | |
| 23 | + | end |
| @@ -0,0 +1,15 @@ | |||
| 1 | + | local combat = Combat() | |
| 2 | + | combat:setParameter(COMBAT_PARAM_EFFECT, CONST_ME_YELLOW_RINGS) | |
| 3 | + | combat:setArea(createCombatArea(AREA_SQUAREWAVE5)) | |
| 4 | + | ||
| 5 | + | local parameters = { | |
| 6 | + | {key = CONDITION_PARAM_TICKS, value = 5 * 1000}, | |
| 7 | + | {key = CONDITION_PARAM_SKILL_DISTANCEPERCENT, value = 80} | |
| 8 | + | } | |
| 9 | + | ||
| 10 | + | function onCastSpell(creature, variant) | |
| 11 | + | for _, target in ipairs(combat:getTargets(creature, variant)) do | |
| 12 | + | target:addAttributeCondition(parameters) | |
| 13 | + | end | |
| 14 | + | return true | |
| 15 | + | end |
| @@ -0,0 +1,12 @@ | |||
| 1 | + | local combat = Combat() | |
| 2 | + | combat:setParameter(COMBAT_PARAM_TYPE, COMBAT_DEATHDAMAGE) | |
| 3 | + | combat:setParameter(COMBAT_PARAM_EFFECT, CONST_ME_SMALLCLOUDS) | |
| 4 | + | combat:setArea(createCombatArea(AREA_CIRCLE6X6)) | |
| 5 | + | ||
| 6 | + | function onCastSpell(creature, variant) | |
| 7 | + | local damage = math.random(52, 154) | |
| 8 | + | for _, target in ipairs(combat:getTargets(creature, variant)) do | |
| 9 | + | creature:addDamageCondition(target, CONDITION_CURSED, DAMAGELIST_EXPONENTIAL_DAMAGE, damage) | |
| 10 | + | end | |
| 11 | + | return true | |
| 12 | + | end |
| @@ -0,0 +1,11 @@ | |||
| 1 | + | local combat = Combat() | |
| 2 | + | combat:setParameter(COMBAT_PARAM_TYPE, COMBAT_DROWNDAMAGE) | |
| 3 | + | combat:setParameter(COMBAT_PARAM_EFFECT, CONST_ME_BUBBLES) | |
| 4 | + | combat:setArea(createCombatArea(AREA_CIRCLE6X6)) | |
| 5 | + | ||
| 6 | + | function onCastSpell(creature, variant) | |
| 7 | + | for _, target in ipairs(combat:getTargets(creature, variant)) do | |
| 8 | + | creature:addDamageCondition(target, CONDITION_DROWN, DAMAGELIST_CONSTANT_PERIOD, 20, 5, 50) | |
| 9 | + | end | |
| 10 | + | return true | |
| 11 | + | end |
| @@ -0,0 +1,10 @@ | |||
| 1 | + | local combat = Combat() | |
| 2 | + | combat:setParameter(COMBAT_PARAM_TYPE, COMBAT_ENERGYDAMAGE) | |
| 3 | + | combat:setParameter(COMBAT_PARAM_EFFECT, CONST_ME_ENERGYHIT) | |
| 4 | + | ||
| 5 | + | function onCastSpell(creature, variant) | |
| 6 | + | for _, target in ipairs(combat:getTargets(creature, variant)) do | |
| 7 | + | creature:addDamageCondition(target, CONDITION_ENERGY, DAMAGELIST_VARYING_PERIOD, 25, {10, 12}, 20) | |
| 8 | + | end | |
| 9 | + | return true | |
| 10 | + | end |
| @@ -0,0 +1,15 @@ | |||
| 1 | + | local combat = Combat() | |
| 2 | + | combat:setParameter(COMBAT_PARAM_EFFECT, CONST_ME_MAGIC_RED) | |
| 3 | + | combat:setArea(createCombatArea(AREA_CIRCLE2X2)) | |
| 4 | + | ||
| 5 | + | local parameters = { | |
| 6 | + | {key = CONDITION_PARAM_TICKS, value = 6 * 1000}, | |
| 7 | + | {key = CONDITION_PARAM_SKILL_DISTANCEPERCENT, value = 50} | |
| 8 | + | } | |
| 9 | + | ||
| 10 | + | function onCastSpell(creature, variant) | |
| 11 | + | for _, target in ipairs(combat:getTargets(creature, variant)) do | |
| 12 | + | target:addAttributeCondition(parameters) | |
| 13 | + | end | |
| 14 | + | return true | |
| 15 | + | end |
| @@ -0,0 +1,15 @@ | |||
| 1 | + | local combat = Combat() | |
| 2 | + | combat:setParameter(COMBAT_PARAM_EFFECT, CONST_ME_SOUND_PURPLE) | |
| 3 | + | combat:setArea(createCombatArea(AREA_SQUAREWAVE6)) | |
| 4 | + | ||
| 5 | + | local parameters = { | |
| 6 | + | {key = CONDITION_PARAM_TICKS, value = 8 * 1000}, | |
| 7 | + | {key = CONDITION_PARAM_SKILL_SHIELDPERCENT, value = 85} | |
| 8 | + | } | |
| 9 | + | ||
| 10 | + | function onCastSpell(creature, variant) | |
| 11 | + | for _, target in ipairs(combat:getTargets(creature, variant)) do | |
| 12 | + | target:addAttributeCondition(parameters) | |
| 13 | + | end | |
| 14 | + | return true | |
| 15 | + | end |
| @@ -0,0 +1,12 @@ | |||
| 1 | + | local combat = Combat() | |
| 2 | + | combat:setParameter(COMBAT_PARAM_TYPE, COMBAT_DEATHDAMAGE) | |
| 3 | + | combat:setParameter(COMBAT_PARAM_EFFECT, CONST_ME_SMALLCLOUDS) | |
| 4 | + | combat:setParameter(COMBAT_PARAM_DISTANCEEFFECT, CONST_ANI_DEATH) | |
| 5 | + | ||
| 6 | + | function onCastSpell(creature, variant) | |
| 7 | + | local damage = math.random(17, 36) | |
| 8 | + | for _, target in ipairs(combat:getTargets(creature, variant)) do | |
| 9 | + | creature:addDamageCondition(target, CONDITION_CURSED, DAMAGELIST_EXPONENTIAL_DAMAGE, damage) | |
| 10 | + | end | |
| 11 | + | return true | |
| 12 | + | end |
| @@ -0,0 +1,20 @@ | |||
| 1 | + | local combat = Combat() | |
| 2 | + | combat:setParameter(COMBAT_PARAM_EFFECT, CONST_ME_STUN) | |
| 3 | + | combat:setParameter(COMBAT_PARAM_DISTANCEEFFECT, CONST_ANI_EXPLOSION) | |
| 4 | + | combat:setArea(createCombatArea(AREA_BEAM1)) | |
| 5 | + | ||
| 6 | + | local parameters = { | |
| 7 | + | {key = CONDITION_PARAM_TICKS, value = 8 * 1000}, | |
| 8 | + | {key = CONDITION_PARAM_SKILL_MELEEPERCENT, value = nil}, | |
| 9 | + | {key = CONDITION_PARAM_SKILL_DISTANCEPERCENT, value = nil} | |
| 10 | + | } | |
| 11 | + | ||
| 12 | + | function onCastSpell(creature, variant) | |
| 13 | + | parameters[2].value = math.random(45, 65) | |
| 14 | + | parameters[3].value = parameters[2].value | |
| 15 | + | ||
| 16 | + | for _, target in ipairs(combat:getTargets(creature, variant)) do | |
| 17 | + | target:addAttributeCondition(parameters) | |
| 18 | + | end | |
| 19 | + | return true | |
| 20 | + | end |