Ir para conteúdo

Erro Ao Separar Funções Em Diferentes Scripts


luishg

Posts Recomendados

Informações Gerais:

Server: OTServ 0.6.3

Versão: 8.60

Erro: "attempt to call global 'drainSpell'(a nil value)"

 

Introdução:

Bom eu sou programador C++ e C#, iniciei há pouco tempo com LUA, então estou tendo alguns probleminhas.

Eu desenvolvi uma Spell que funciona perfeitamente. O Código está abaixo:

 

spellCompleta.lua

-- Arquivo spells/scripts/spellCompleta.lua   - funcionando - OK.
local combat = createCombatObject()
setCombatParam(combat, COMBAT_PARAM_AGGRESSIVE, false)

function onCastSpell(cid, var)
	if getPlayerStorageValue(cid, 11000) == 1 then
		stopSpell(cid)
	end  
	addEvent(startSpell, 3000, cid)
	setPlayerStorageValue(cid, 11000, 1)
	drainSpell(cid)

 return doCombat(cid, combat, var)
end

function startSpell(cid)
	 doSendMagicEffect(getCreaturePosition(cid), 2)
	doCreatureChangeOutfit(cid, {lookType = 28})
end	

function stopSpell(cid)
	setPlayerStorageValue(cid, 11000, 0)
	doRemoveCondition(cid, CONDITION_OUTFIT)
	doCreatureChangeOutfit(cid, {lookType = 29})
end

function drainSpell(cid)
	if isPlayer(cid) then
		if getPlayerStorageValue(cid, 11000) == 1 and getPlayerMana(cid) > 0 then
			doPlayerAddMana(cid, -1)
			addEvent(drainSpell, 3000, cid)
		elseif getPlayerMana(cid) == 0 then
			doSendMagicEffect(getCreaturePosition(cid), 2)
			stopSpell(cid)		  
			doPlayerSendCancel(cid, "Spell has been interrupted. You're out of mana.")
		end
	end
end

 

Situação:

Eu pretendo desenvolver a Spell1, Spell2, Spell3 e assim por diante, e todas elas são no mesmo modelo, pois todas elas precisam ter o mesmo: startSpell, StopSpell e drainSpell.

Então por lógica, criei um Script separado para deixar tais funções, ele se chama standardSpell.

Neste exemplo eu removo a function "drainSpell" do arquivo "spell1.lua", e coloco ela somente no arquivo standardSpell.

 

spell1.lua

-- Arquivo spells/scripts/spell1.lua
local combat = createCombatObject()
setCombatParam(combat, COMBAT_PARAM_AGGRESSIVE, false)
function onCastSpell(cid, var)
	if getPlayerStorageValue(cid, 11000) == 1 then
		stopSpell(cid)
	end
	addEvent(startSpell, 3000, cid)
	setPlayerStorageValue(cid, 11000, 1)
	drainSpell(cid)

 return doCombat(cid, combat, var)
end
function startSpell(cid)
	 doSendMagicEffect(getCreaturePosition(cid), 2)
	doCreatureChangeOutfit(cid, {lookType = 28})
end	
function stopSpell(cid)
	setPlayerStorageValue(cid, 11000, 0)
	doRemoveCondition(cid, CONDITION_OUTFIT)
	doCreatureChangeOutfit(cid, {lookType = 29})
end

 

standardSpell.lua

-- Arquivo spells/scripts/standardSpell.lua
function drainSpell(cid)
	if isPlayer(cid) then
		if getPlayerStorageValue(cid, 11000) == 1 and getPlayerMana(cid) > 0 then
			doPlayerAddMana(cid, -1)
			addEvent(drainSpell, 3000, cid)
		elseif getPlayerMana(cid) == 0 then
			doSendMagicEffect(getCreaturePosition(cid), 2)
			stopSpell(cid)		  
			doPlayerSendCancel(cid, "Spell has been interrupted. You're out of mana.")
		end
	end
end

 

Ao remover o drainSpell do arquivo "spell1.lua" e adicioná-lo no "standardSpell.lua" eu passo a receber o seguinte erro: "attempt to call global 'drainSpell'(a nil value)".

 

Conclusão:

Gostaria de saber o porquê deste erro e como fazer para criar e utilizar funções "genéricas", que serão chamados/utilizadas por diversos scripts.

 

 

Obs: O código está um pouco menor e simplificado por Spell1, Spell2 para ser mais prático e objetivo.

Obs2: Coloquei em anexo o código com a spell normal funcionando, e o código com ela dividida em "spell1.lua" e "standardSpell.lua".

 

Obg e att,

Luís.

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

Esse tipo de função deve ser colocada na libs para os arquivos poderem identificar. Vai em data/lib/ duplica um arquivo e renomeia para qualquer coisa, depois sóh abre e cola a função drainSpell. Acho que isso resolvera teu problema.

Link para o comentário
Compartilhar em outros sites

Esse tipo de função deve ser colocada na libs para os arquivos poderem identificar. Vai em data/lib/ duplica um arquivo e renomeia para qualquer coisa, depois sóh abre e cola a função drainSpell. Acho que isso resolvera teu problema.

 

Bom, na distro OTServ 0.6.3 não há a pasta data/lib. Eu já havia tentado colocar na pasta data/spells/lib, que por lógica deveria fazer com que fosse aberta antes dos scripts, mas o erro continua a acontecer.

Baixei o TFS, e nele há a pasta data/lib, colocando ali funciona 100%.

 

Embora não tenha achado solução para a distro OTServ 0.6.3, pode fechar o tópico, pois passarei a utilizar o TFS mesmo e nele está funcionando de acordo com o que o Jhon falou.

 

Obg,

Luís.

Link para o comentário
Compartilhar em outros sites

Você pode tentar criar uma LIB para as mesmas em data/lib/xxx-standspells.lua com o seguinte conteúdo:

function startSpell(cid)
                doSendMagicEffect(getCreaturePosition(cid), 2)
               doCreatureChangeOutfit(cid, {lookType = 28})
end     
function stopSpell(cid)
               setPlayerStorageValue(cid, 11000, 0)
               doRemoveCondition(cid, CONDITION_OUTFIT)
               doCreatureChangeOutfit(cid, {lookType = 29})
end
function drainSpell(cid)
               if isPlayer(cid) then
                       if getPlayerStorageValue(cid, 11000) == 1 and getPlayerMana(cid) > 0 then
                               doPlayerAddMana(cid, -1)
                               addEvent(drainSpell, 3000, cid)
                       elseif getPlayerMana(cid) == 0 then
                               doSendMagicEffect(getCreaturePosition(cid), 2)
                               stopSpell(cid)            
                               doPlayerSendCancel(cid, "Spell has been interrupted. You're out of mana.")
                       end
               end
end

 

E colocar na primeira linha (de preferência) do arquivo que quiser usar tais funções isto:

dofile("./data/lib/xxx-standspells.lua")

Link para o comentário
Compartilhar em outros sites

×
×
  • Criar Novo...