Ir para conteúdo

Sistema anti-pega-e-corre (quest)


warotserv

Posts Recomendados

Bom dia. Como muitos devem saber a prática de se completar uma quest de baú e depois sair correndo (sem matar os monstros por perto) é muito comum. Com isso, decidi implementar um sistema simples de impedir que isso aconteça.

Primeiramente, darei uma visão geral do que é verificado para que o player tenha sucesso na quest. O player não poderá estar a X SQM de distância do baú de quest. O player não poderá estar em uma andar diferente do baú de quest.

Agora explicando o que deve ser feito.

No arquivo de sua quest, cole o seguinte código

-- this table will store the players who are on delay to have their quest completed (successfully or not)
playersCompletingQuests = {}

local checkingEventDelay = 250
local checkingEventTimes = 60
local maxDistanceToBeCompleted = 7 -- SQM

function getDistance (pos1, pos2) -- get distance between two positions (using tibia formula)
    local difX = pos1.x - pos2.x
    local difY = pos1.y - pos2.y
    local difZ = pos1.z - pos2.z
    
    -- math.abs() of difs
    if difX < 0 then difX = -difX end
    if difY < 0 then difY = -difY end
    if difZ < 0 then difZ = -difZ end
    
    -- using tibia formula
    local maxDif = difX
    if maxDif < difY then maxDif = difY end
    if maxDif < difZ then maxDif = difZ end
    
    -- return the result
    return maxDif
end

-- To be completed, it's essential that player stays nearby the chest AND at the same floor.
function canBeCompleted(cid, item, topos) -- checks if player respected the delay and distance
    -- check if player is on-line or if it died during the delay time
    if not isPlayer(cid) then return false end
    
    -- store player position in a variable
    local playerPos = getCreaturePosition(cid)
    
    -- check if the distance between player and chest is below the maximum allowed
    if getDistance(playerPos, topos) > maxDistanceToBeCompleted then return false end
    
    -- check same floor condition
    if playerPos.z ~= topos.z then return false end
    
    -- reach here means the player can receive its awards
    return true
end

function completeQuest(cid, item, topos) --Event will call this
    -- remove the player from playersCompletingQuests
    playersCompletingQuests[cid] = nil
    
    -- give player it's awards!!!    
    --double checking if the player hasn't done the quest yet
    if not questAlreadyCompleted(cid, item) then
        doCreatureSay(cid, "COMPLETEI UMA QUEST!!", TALKTYPE_ORANGE_1)
        doPlayerSendTextMessage(cid,22,"Voce completou a quest, parabens!")
        
        -- AQUI VOCÊ IMPLEMENTARÁ A PARTE DE ENTREGAR O PRÊMIO AO PLAYER
        
-- AQUI VOCÊ IMPLEMENTARÁ A PARTE DE ACRESCENTAR A STORAGE AO PLAYER
    else
        doPlayerSendTextMessage(cid,22,"Voce ja completou essa quest.")
    end
end

function checkingEvent(cid, item, topos, checkingsLeft)
    if checkingsLeft <= 0 then
        completeQuest(cid, item, topos)
    else
        if canBeCompleted(cid, item, topos) then
            doCreatureSay(cid, checkingsLeft, TALKTYPE_ORANGE_1)
            addEvent(checkingEvent, checkingEventDelay, cid, item, topos, checkingsLeft-1)
        else -- cannot be completed
            if isPlayer(cid) then -- is player online?
                doCreatureSay(cid, "fail", TALKTYPE_ORANGE_1)
                doPlayerSendTextMessage(cid,22,"Voce falhou em completar a quest. tente novamente!")
            end
            -- remove the player from playersCompletingQuests
            playersCompletingQuests[cid] = nil
        end
    end
end

function questAlreadyCompleted(cid, item)
    local queststatus = getPlayerStorageValue(cid,STORAGE_NUMBER) -- COLOQUE O STORAGE NUMBER DA QUEST AQUI!!!!!!
    if queststatus == -1 then
        return false
    else
        return true
    end
end

function isOnAnotherQuest(cid)
    if playersCompletingQuests[cid] == true then
        return true
    else
        return false
    end
end

function onUse(cid, item, frompos, item2, topos)
    if questAlreadyCompleted(cid, item) then
        doPlayerSendTextMessage(cid,22,"Voce ja completou essa quest.")
    elseif isOnAnotherQuest(cid) then
        doPlayerSendTextMessage(cid,22,"Voce ja esta tentando completar uma outra quest. Aguarde!")
    else
        playersCompletingQuests[cid] = true -- player is now trying to achieve success in a quest
        addEvent(checkingEvent, 0, cid, item, topos, checkingEventTimes)
    end
    return true
end

Agora, faça as devidas mudanças, para se adaptar à sua quest,

em:

-- AQUI VOCÊ IMPLEMENTARÁ A PARTE DE ENTREGAR O PRÊMIO AO PLAYER
-- AQUI VOCÊ IMPLEMENTARÁ A PARTE DE ACRESCENTAR A STORAGE AO PLAYER
local queststatus = getPlayerStorageValue(cid,STORAGE_NUMBER) -- COLOQUE O STORAGE NUMBER DA QUEST AQUI!!!!!!

 

 

faça o que se pede.
Agora, explicando o que pode ser configurado:

 

 

ocal checkingEventDelay = 250
local checkingEventTimes = 60
local maxDistanceToBeCompleted = 7 -- SQM

 

checkingEventDelay representa de quanto em quanto tempo (em milissegundos) a função "checkingEvent" será chamada.

 

checkingEventTimes representa quantas vezes a função "checkingEvent" será chamada.

maxDistanceToBeCompleted representa qual é a distancia máxima que o player pode se distanciar do baú, para que a quest não falhe.

Bom, é isso.

Espero ter ajudado.

P.S.: Não me importo que roubem meus créditos e/ou postem em outros fórums.

Link para o comentário
Compartilhar em outros sites

Discordo com você lordbug99.

 

O script ficou gigante? ficou. Mas caso você saiba fazer um gerenciador de quests, esse não será o problema.

 

Caso queira aprender, por favor, só me falar.

Editado por warotserv
Link para o comentário
Compartilhar em outros sites

Tamanho de script não representa qualidade. Isso, por maior que fique, vai apresentar apenas alguns milissegundos de diferença, imperceptível para o jogador.

 

Poderia ser reduzido? Sim, poderia. Mas muitas vezes é até melhor ficar grande por uma questão de organização. É perfeitamente possível fazer um script de teletransportar um jogador até uma coordenada específica, cobrando dinheiro e verificando level em apenas um único return. Mas fazer isso deixaria o script deveras desorganizado.

 

E se o dono do server quer criar um servidor bem profissional, bloquear as saídas ficaria meio gambiarra, o que não é muito legal.

Link para o comentário
Compartilhar em outros sites

Concordo com o pessoal, funções sem necessidade e muitos comentários, se você souber fazer um script claro, não vai precisar comentar uma linha que todos vão entender o que esta se passando nele.

Link para o comentário
Compartilhar em outros sites

E se o dono do server quer criar um servidor bem profissional, bloquear as saídas ficaria meio gambiarra, o que não é muito legal.

90% dos jogos de rpg fazem isso(muitos mmorpg tbm)...

 

@warotserv

anyway, seria melhor se o cara so pudese abrir o bau após matar os mobs, porque n faz sentido vc abrir o bau e receber apenas depois de certo tempo.

 

e já que vc fez um comentario falando sobre ensinar alguma coisa, deveria pelo menos saber o que é uma quest e o que uma treasure chest, são coisas bem differentes....

Link para o comentário
Compartilhar em outros sites

 

E se o dono do server quer criar um servidor bem profissional, bloquear as saídas ficaria meio gambiarra, o que não é muito legal.

90% dos jogos de rpg fazem isso(muitos mmorpg tbm)...

 

@warotserv

anyway, seria melhor se o cara so pudese abrir o bau após matar os mobs, porque n faz sentido vc abrir o bau e receber apenas depois de certo tempo.

 

e já que vc fez um comentario falando sobre ensinar alguma coisa, deveria pelo menos saber o que é uma quest e o que uma treasure chest, são coisas bem differentes....

 

 

Falei "quem quiser fazer um servidor bem profissional". No caso, tô me referindo a Tibia, outros MMO não entram nesse quesito. Se você dissesse "90% dos servidores de Tibia", aí eu já digo: Por isso disse "quem quiser fazer um servidor bem profissional". 90% dos servidores existentes de tibia são só coisas zoadas mesmo.

 

E de qualquer maneira, galera, vamo parar de discussão. Vocês já tão brigando por opinião, que é bem errado por ser algo subjetivo, que varia de cada um pra cada um.

Editado por LuckOake
Link para o comentário
Compartilhar em outros sites

×
×
  • Criar Novo...