• There is NO official Otland's Discord server and NO official Otland's server list. The Otland's Staff does not manage any Discord server or server list. Moderators or administrator of any Discord server or server lists have NO connection to the Otland's Staff. Do not get scammed!

TFS 1.X+ console error

johnsamir

Advanced OT User
Joined
Oct 13, 2009
Messages
1,083
Solutions
6
Reaction score
191
Location
Nowhere
Lua:
Lua Script Error: [Scripts Interface]
C:\Users\pasturryx\OneDrive\Documentos\GitHub\pro-ot\data\scripts\eventcallbacks\player\default_onLookInMarket.lua
...entos\GitHub\pro-ot\data\scripts/lib\event_callbacks.lua:101: bad argument #1 to 'insert' (table expected, got nil)
stack traceback:
        [C]: in function 'insert'
        ...entos\GitHub\pro-ot\data\scripts/lib\event_callbacks.lua:101: in function 'register'
        ...scripts\eventcallbacks\player\default_onLookInMarket.lua:311: in main chunk
> default_onLookInMarket.lua [error]
^
my eventcallback.lua
Code:
-- Creature
EVENT_CALLBACK_ONCHANGEOUTFIT = 1
EVENT_CALLBACK_ONCHANGEMOUNT = 2
EVENT_CALLBACK_ONAREACOMBAT = 3
EVENT_CALLBACK_ONTARGETCOMBAT = 4
EVENT_CALLBACK_ONHEAR = 5
-- Party
EVENT_CALLBACK_ONJOIN = 6
EVENT_CALLBACK_ONLEAVE = 7
EVENT_CALLBACK_ONDISBAND = 8
EVENT_CALLBACK_ONSHAREEXPERIENCE = 9
-- Player
EVENT_CALLBACK_ONBROWSEFIELD = 10
EVENT_CALLBACK_ONLOOK = 11
EVENT_CALLBACK_ONLOOKINBATTLELIST = 12
EVENT_CALLBACK_ONLOOKINTRADE = 13
EVENT_CALLBACK_ONLOOKINSHOP = 14
EVENT_CALLBACK_ONTRADEREQUEST = 15
EVENT_CALLBACK_ONTRADEACCEPT = 16
EVENT_CALLBACK_ONTRADECOMPLETED = 17
EVENT_CALLBACK_ONMOVEITEM = 18
EVENT_CALLBACK_ONITEMMOVED = 19
EVENT_CALLBACK_ONMOVECREATURE = 20
EVENT_CALLBACK_ONREPORTRULEVIOLATION = 21
EVENT_CALLBACK_ONREPORTBUG = 22
EVENT_CALLBACK_ONTURN = 23
EVENT_CALLBACK_ONGAINEXPERIENCE = 24
EVENT_CALLBACK_ONLOSEEXPERIENCE = 25
EVENT_CALLBACK_ONGAINSKILLTRIES = 26
EVENT_CALLBACK_ONWRAPITEM = 27
-- Monster
EVENT_CALLBACK_ONDROPLOOT = 28
EVENT_CALLBACK_ONSPAWN = 29
EVENT_CALLBACK_ONLOOKINMARKET = 30
-- last (for correct table counting)
EVENT_CALLBACK_LAST = EVENT_CALLBACK_ONSPAWN

local callbacks = {
    -- Creature
    ["onChangeOutfit"] = EVENT_CALLBACK_ONCHANGEOUTFIT,
    ["onChangeMount"] = EVENT_CALLBACK_ONCHANGEMOUNT,
    ["onAreaCombat"] = EVENT_CALLBACK_ONAREACOMBAT,
    ["onTargetCombat"] = EVENT_CALLBACK_ONTARGETCOMBAT,
    ["onHear"] = EVENT_CALLBACK_ONHEAR,
    -- Party
    ["onJoin"] = EVENT_CALLBACK_ONJOIN,
    ["onLeave"] = EVENT_CALLBACK_ONLEAVE,
    ["onDisband"] = EVENT_CALLBACK_ONDISBAND,
    ["onShareExperience"] = EVENT_CALLBACK_ONSHAREEXPERIENCE,
    -- Player
    ["onBrowseField"] = EVENT_CALLBACK_ONBROWSEFIELD,
    ["onLook"] = EVENT_CALLBACK_ONLOOK,
    ["onLookInBattleList"] = EVENT_CALLBACK_ONLOOKINBATTLELIST,
    ["onLookInTrade"] = EVENT_CALLBACK_ONLOOKINTRADE,
    ["onLookInShop"] = EVENT_CALLBACK_ONLOOKINSHOP,
    ["onTradeRequest"] = EVENT_CALLBACK_ONTRADEREQUEST,
    ["onTradeAccept"] = EVENT_CALLBACK_ONTRADEACCEPT,
    ["onTradeCompleted"] = EVENT_CALLBACK_ONTRADECOMPLETED,
    ["onMoveItem"] = EVENT_CALLBACK_ONMOVEITEM,
    ["onItemMoved"] = EVENT_CALLBACK_ONITEMMOVED,
    ["onMoveCreature"] = EVENT_CALLBACK_ONMOVECREATURE,
    ["onReportRuleViolation"] = EVENT_CALLBACK_ONREPORTRULEVIOLATION,
    ["onReportBug"] = EVENT_CALLBACK_ONREPORTBUG,
    ["onTurn"] = EVENT_CALLBACK_ONTURN,
    ["onGainExperience"] = EVENT_CALLBACK_ONGAINEXPERIENCE,
    ["onLoseExperience"] = EVENT_CALLBACK_ONLOSEEXPERIENCE,
    ["onGainSkillTries"] = EVENT_CALLBACK_ONGAINSKILLTRIES,
    ["onWrapItem"] = EVENT_CALLBACK_ONWRAPITEM,
    ["onLookInMarket"] = EVENT_CALLBACK_ONLOOKINMARKET,
    -- Monster
    ["onDropLoot"] = EVENT_CALLBACK_ONDROPLOOT,
    ["onSpawn"] = EVENT_CALLBACK_ONSPAWN
}

local updateableParameters = {
    [EVENT_CALLBACK_ONLOOK] = {[5] = 1},
    [EVENT_CALLBACK_ONLOOKINBATTLELIST] = {[4] = 1},
    [EVENT_CALLBACK_ONLOOKINTRADE] = {[5] = 1},
    [EVENT_CALLBACK_ONLOOKINSHOP] = {[4] = 1},
    [EVENT_CALLBACK_ONGAINEXPERIENCE] = {[3] = 1},
    [EVENT_CALLBACK_ONLOSEEXPERIENCE] = {[2] = 1},
    [EVENT_CALLBACK_ONGAINSKILLTRIES] = {[3] = 1}
}

EventCallbackData = {}
hasEventCallback = function (type)
    return #EventCallbackData[type] > 0
end

EventCallback = {
    register = function (self, triggerIndex)
        if isScriptsInterface() then
            local eventType = rawget(self, 'eventType')
            local callback = rawget(self, 'callback')
            if not eventType or not callback then
                debugPrint("[Warning - EventCallback::register] need to setup a callback before you can register.")
                return
            end

            local eventData = EventCallbackData[eventType]
            table.insert(eventData, {
                callback = callback,
                triggerIndex = tonumber(triggerIndex) or 0
            })
            table.sort(eventData, function (ecl, ecr) return ecl.triggerIndex < ecr.triggerIndex end)
            rawset(self, 'eventType', nil)
            rawset(self, 'callback', nil)
            return true
        end
    end,

    clear = function (self)
        EventCallbackData = {}
        for i = 1, EVENT_CALLBACK_LAST do
            EventCallbackData[i] = {}
        end
        return true
    end
}

setmetatable(EventCallback, {
    __index = function (self, key)
        return nil
    end,

    __call = function (self, eventCallback, ...)
        local eventData = EventCallbackData[eventCallback]
        local results = {}
        local eventDataCount = #eventData
        local args = table.pack(...)
        for index, event in pairs(eventData) do
            repeat
                results = {event.callback(unpack(args))}
                local output = results[1]
                -- If the call returns nil then we continue with the next call
                if output == nil then
                    break
                end
                -- If the call returns false then we exit the loop
                if output == false then
                    return false
                end
                -- If the call of type returnvalue returns noerror then we continue the loop
                if table.contains({EVENT_CALLBACK_ONAREACOMBAT, EVENT_CALLBACK_ONTARGETCOMBAT}, eventCallback) then
                    if output == RETURNVALUE_NOERROR then
                        break
                    end
                    
                    return output
                end
                -- We left the loop why have we reached the end
                if index == eventDataCount then
                    return unpack(results)
                end
            until true

            -- Update the results for the next call
            local parameters = updateableParameters[eventCallback]
            if parameters then
                for index, value in pairs(parameters) do
                    args[index] = results[value]
                end
            end
        end
    end,

    __newindex = function (self, key, callback)
        if not isScriptsInterface() then
            return
        end

        local eventType = callbacks[key]
        if not eventType then
            debugPrint(string.format("[Warning - EventCallback::%s] is not a valid callback.", key))
            return
        end

        if type(callback) ~= "function" then
            debugPrint(string.format("[Warning - EventCallback::%s] a function is expected.", key))
            return
        end

        rawset(self, 'eventType', eventType)
        rawset(self, 'callback', callback)
    end
})

-- can't be overwritten on reloads
EventCallback:clear()
Code:
defaultonlookmarket.lua
local showAtkWeaponTypes = {WEAPON_CLUB, WEAPON_SWORD, WEAPON_AXE, WEAPON_DISTANCE}
local showDefWeaponTypes = {WEAPON_CLUB, WEAPON_SWORD, WEAPON_AXE, WEAPON_DISTANCE, WEAPON_SHIELD}

local ec = EventCallback

ec.onLookInMarket = function(self, itemType)
    local response = NetworkMessage()
    response:addByte(0xF8)
    response:addU16(itemType:getClientId())

    -- tier label (byte)
    do
        if itemType:getClassification() > 0 then
            response:addByte(0)
        end
    end

    -- armor
    do
        local armor = itemType:getArmor()
        if armor > 0 then
            response:addString(armor)
        else
            response:addU16(0)
        end
    end

    -- weapon data (will be reused)
    local weaponType = itemType:getWeaponType()

    -- attack
    do
        local showAtk = table.contains(showAtkWeaponTypes, weaponType)
        if showAtk then
            local atkAttrs = {}
            local atk = itemType:getAttack()
            if itemType:isBow() then
                if atk ~= 0 then
                    atkAttrs[#atkAttrs + 1] = string.format("%+d", atk)
                end

                local hitChance = itemType:getHitChance()
                if hitChance ~= 0 then
                    atkAttrs[#atkAttrs + 1] = string.format("chance to hit %+d%%", hitChance)
                end

                atkAttrs[#atkAttrs + 1] = string.format("%d fields", itemType:getShootRange())
            else
                atkAttrs[#atkAttrs + 1] = atk
                local elementDmg = itemType:getElementDamage()
                if elementDmg ~= 0 then
                    atkAttrs[#atkAttrs] = string.format("%d physical %+d %s", atkAttrs[#atkAttrs], elementDmg, getCombatName(itemType:getElementType()))
                end
            end

            response:addString(table.concat(atkAttrs, ", "))
        else
            response:addU16(0)
        end
    end

    -- container slots
    do
        if itemType:isContainer() then
            response:addString(itemType:getCapacity())
        else
            response:addU16(0)
        end
    end

    -- defense
    do
        local showDef = table.contains(showDefWeaponTypes, weaponType)
        if showDef then
            local def = itemType:getDefense()
            if weaponType == WEAPON_DISTANCE then
                -- throwables
                local ammoType = itemType:getAmmoType()
                if ammoType ~= AMMO_ARROW and ammoType ~= AMMO_BOLT then
                    response:addString(def)
                else
                    response:addU16(0)
                end
            else
                -- extra def
                local xD = itemType:getExtraDefense()
                if xD ~= 0 then
                    def = string.format("%d %+d", def, xD)
                end

                response:addString(def)
            end
        else
            response:addU16(0)
        end
    end

    -- description
    do
        local desc = itemType:getDescription()
        if desc and #desc > 0 then
            response:addString(desc:sub(1, -2))
        else
            response:addU16(0)
        end
    end

    -- duration
    do
        local duration = itemType:getDuration()
        if duration == 0 then
            local transferType = itemType:getTransformEquipId()
            if transferType ~= 0 then
                transferType = ItemType(transferType)
                duration = transferType and transferType:getDuration() or duration
            end
        end

        if duration > 0 then
            response:addString(Game.getCountdownString(duration, true, true))
        else
            response:addU16(0)
        end
    end

    -- item abilities (will be reused)
    local abilities = itemType:getAbilities()

    -- element protections
    do
        local protections = {}
        for element, value in pairs(abilities.absorbPercent) do
            if value ~= 0 then
                protections[#protections + 1] = string.format("%s %+d%%", getCombatName(2 ^ (element - 1)), value)
            end
        end

        if #protections > 0 then
            response:addString(table.concat(protections, ", "))
        else
            response:addU16(0)
        end
    end

    -- level req
    do
        local minLevel = itemType:getMinReqLevel()
        if minLevel > 0 then
            response:addString(minLevel)
        else
            response:addU16(0)
        end
    end

    -- magic level req
    do
        local minMagicLevel = itemType:getMinReqMagicLevel()
        if minMagicLevel > 0 then
            response:addString(minMagicLevel)
        else
            response:addU16(0)
        end
    end

    -- vocation
    do
        local vocations = itemType:getVocationString()
        if vocations and vocations:len() > 0 then
            response:addString(vocations)
        else
            response:addU16(0)
        end
    end

    -- rune words
    do
        local spellName = itemType:getRuneSpellName()
        if spellName and spellName:len() > 0 then
            response:addString(spellName)
        else
            response:addU16(0)
        end
    end

    -- "skill boost" category
    do
        -- atk speed
        local atkSpeed = itemType:getAttackSpeed()
        local skillBoosts = {}
        if atkSpeed ~= 0 then
            skillBoosts[#skillBoosts + 1] = string.format("attack speed %0.2f/turn", 2000 / atkSpeed)
        end

        -- skill boost
        if abilities.manaGain > 0 or abilities.healthGain > 0 or abilities.regeneration then
            skillBoosts[#skillBoosts + 1] = "faster regeneration"
        end

        -- invisibility
        if abilities.invisible then
            skillBoosts[#skillBoosts + 1] = "invisibility"
        end

        -- magic shield (classic)
        if abilities.manaShield then
            skillBoosts[#skillBoosts + 1] = "magic shield"
        end

        -- stats (hp/mp/soul/ml)
        for stat, value in pairs(abilities.stats) do
            if value ~= 0 then
                skillBoosts[#skillBoosts + 1] = string.format("%s %+d", getStatName(stat - 1), value)
            end
        end

        -- stats but in %
        for stat, value in pairs(abilities.statsPercent) do
            if value ~= 0 then
                skillBoosts[#skillBoosts + 1] = string.format("%s %+d%%", getStatName(stat - 1), value)
            end
        end

        -- speed
        if abilities.speed ~= 0 then
            skillBoosts[#skillBoosts + 1] = string.format("speed %+d", math.floor(abilities.speed / 2))
        end

        -- skills
        for skill, value in pairs(abilities.skills) do
            if value ~= 0 then
                skillBoosts[#skillBoosts + 1] = string.format("%s %+d", getSkillName(skill - 1), value)
            end
        end

        -- special skills
        for skill, value in pairs(abilities.specialSkills) do
            if value ~= 0 then
                skillBoosts[#skillBoosts + 1] = string.format("%s %+d", getSpecialSkillName[skill - 1], value)
            end
        end

        -- add to response
        if #skillBoosts > 0 then
            response:addString(table.concat(skillBoosts, ", "))
        else
            response:addU16(0)
        end
    end

    -- charges
    do
        if itemType:hasShowCharges() then
            response:addString(itemType:getCharges())
        else
            response:addU16(0)
        end
    end

    -- weapon type
    do
        if itemType:isWeapon() then
            response:addString(itemType:getWeaponString())
        else
            response:addU16(0)
        end
    end

    -- weight
    response:addString(string.format("%0.2f", itemType:getWeight() / 100))

    -- to do
    response:addU16(0) -- Imbuement Slots
    response:addU16(0) -- Magic Shield Capacity
    response:addU16(0) -- Cleave
    response:addU16(0) -- Damage Reflection
    response:addU16(0) -- Perfect Shot
    response:addU16(0) -- Classification
    response:addU16(0) -- Tier

    -- buy stats
    do
        local stats = itemType:getMarketBuyStatistics()
        if stats then
            response:addByte(0x01)
            response:addU32(stats.numTransactions)
            response:addU64(stats.totalPrice)
            response:addU64(stats.highestPrice)
            response:addU64(stats.lowestPrice)
        else
            response:addByte(0x00)
        end
    end

    -- sell stats
    do
        local stats = itemType:getMarketSellStatistics()
        if stats then
            response:addByte(0x01)
            response:addU32(stats.numTransactions)
            response:addU64(stats.totalPrice)
            response:addU64(stats.highestPrice)
            response:addU64(stats.lowestPrice)
        else
            response:addByte(0x00)
        end
    end

    response:sendToPlayer(self)
end

ec:register()
 
Back
Top