Difference between revisions of "Module:Items"
From Melvor Idle
Inconvenient (talk | contribs) (testing autogenerated item table partial) |
Falterfire (talk | contribs) (Added a check for level requirements to the 'hasCombatStats' check for autoarmourstats just to be safe) |
||
(23 intermediate revisions by 4 users not shown) | |||
Line 6: | Line 6: | ||
local p = {} | local p = {} | ||
− | |||
local ItemData = mw.loadData('Module:Items/data') | local ItemData = mw.loadData('Module:Items/data') | ||
− | |||
− | |||
− | |||
local Constants = require('Module:Constants') | local Constants = require('Module:Constants') | ||
Line 16: | Line 12: | ||
local Icons = require('Module:Icons') | local Icons = require('Module:Icons') | ||
− | p.EasterEggs = {'Amulet of Calculated Promotion', 'Clue Chasers Insignia', '8', 'Lemon'} | + | p.EasterEggs = {'Amulet of Calculated Promotion', 'Clue Chasers Insignia', '8', 'Lemon', 'Easter Egg', 'Abnormal Log', 'Red Herring', 'Cool Glasses'} |
+ | p.EventItems = {'Christmas Cracker', 'Christmas Coal', 'Christmas Sweater', | ||
+ | 'Christmas Wreath', 'Candy Cane', 'Santa Hat', | ||
+ | 'Friendship Bracelet', 'Event Clue 1', 'Event Clue 2', | ||
+ | 'Event Clue 3', 'Event Clue 4', 'Candle', 'Cake Base', | ||
+ | 'Magical Flavouring', 'Magical Icing', 'Birthday Cake', | ||
+ | 'Purple Party Hat', 'Birthday Token', 'Christmas Present (Yellow)', | ||
+ | 'Christmas Present (Blue)', 'Christmas Present (Green)', 'Christmas Present (White)', | ||
+ | 'Christmas Present (Purple)', 'Christmas Present (Standard)', 'Event Token - Holiday 2021', | ||
+ | 'Holiday Scarf', 'Gingerbread House', 'Gingerbread Man', 'Edible Candy Cane', | ||
+ | 'Locked Chest', 'Locked Chest Key', 'Event Token (Holiday 2021)'} | ||
p.OtherShopItems = {'Cooking Gloves', 'Mining Gloves', 'Gem Gloves', 'Smithing Gloves', 'Thieving Gloves'} | p.OtherShopItems = {'Cooking Gloves', 'Mining Gloves', 'Gem Gloves', 'Smithing Gloves', 'Thieving Gloves'} | ||
--This is hardcoded, so there's no easy way to scrape it. Hopefully it doesn't change | --This is hardcoded, so there's no easy way to scrape it. Hopefully it doesn't change | ||
− | p.GemTable = {["Topaz"] = {name = 'Topaz', id = 128, chance = 50}, | + | p.GemTable = {["Topaz"] = {name = 'Topaz', id = 128, chance = 50}, |
− | + | ["Sapphire"] = {name = "Sapphire", id = 129, chance = 17.5}, | |
− | + | ["Ruby"] = {name = "Ruby", id = 130, chance = 17.5}, | |
− | + | ["Emerald"] = {name = "Emerald", id = 131, chance = 10}, | |
− | + | ["Diamond"] = {name = "Diamond", id = 132, chance = 5}} | |
--The base chance to receive a gem while mining | --The base chance to receive a gem while mining | ||
p.GemChance = .01 | p.GemChance = .01 | ||
Line 29: | Line 35: | ||
p.junkCount = 8 | p.junkCount = 8 | ||
--Items (aside from bars & gems) which can be created via Alt Magic | --Items (aside from bars & gems) which can be created via Alt Magic | ||
− | + | p.AltMagicProducts = {'Rune Essence', 'Bones', 'Holy Dust'} | |
--The kinds of gloves with cost & charges | --The kinds of gloves with cost & charges | ||
p.GloveTable = {['Cooking Gloves'] = {cost=50000, charges=500}, | p.GloveTable = {['Cooking Gloves'] = {cost=50000, charges=500}, | ||
− | + | ['Mining Gloves'] = {cost=75000, charges=500}, | |
− | + | ['Smithing Gloves'] = {cost=100000, charges=500}, | |
− | + | ['Thieving Gloves'] = {cost=100000, charges=500}, | |
− | + | ['Gem Gloves'] = {cost=500000, charges=2000}} | |
Line 42: | Line 48: | ||
function p.buildSpecialFishingTable() | function p.buildSpecialFishingTable() | ||
− | + | --This shouldn't ever be included in a page | |
− | + | --This is for generating the above 'specialFishLoot' variable if it ever needs to change | |
− | + | --To re-run, edit the module, type in "console.log(p.buildSpecialFishingTable())" and copy+paste the result as the new value of the variable | |
− | + | --Also gives you the total fishing weight for saving time later | |
− | + | local lootArray = {} | |
− | + | local totalWt = 0 | |
− | + | for i, item in pairs(ItemData.Items) do | |
− | + | if item.fishingCatchWeight ~= nil then | |
− | + | totalWt = totalWt + item.fishingCatchWeight | |
− | + | table.insert(lootArray, '{'..(i - 1)..', '..item.fishingCatchWeight..'}') | |
− | + | end | |
− | + | end | |
− | + | local result = 'p.specialFishWt = '..totalWt..'\r\n' | |
− | + | result = result..'p.specialFishLoot = {'..table.concat(lootArray, ', ')..'}' | |
− | + | return result | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
end | end | ||
function p.getItemByID(ID) | function p.getItemByID(ID) | ||
− | + | local result = Shared.clone(ItemData.Items[ID + 1]) | |
− | + | if result ~= nil then | |
− | + | result.id = ID | |
− | + | end | |
− | + | return result | |
end | end | ||
function p.getItem(name) | function p.getItem(name) | ||
− | + | local result = nil | |
− | + | name = string.gsub(name, "%%27", "'") | |
− | + | name = string.gsub(name, "'", "'") | |
− | + | for i, item in pairs(ItemData.Items) do | |
− | + | local itemName = string.gsub(item.name, '#', '') | |
− | + | if name == itemName then | |
− | + | result = Shared.clone(item) | |
− | + | --Make sure every item has an id, and account for Lua being 1-index | |
− | + | result.id = i - 1 | |
− | + | break | |
− | + | end | |
− | + | end | |
− | + | return result | |
− | |||
end | end | ||
function p.getItems(checkFunc) | function p.getItems(checkFunc) | ||
− | + | local result = {} | |
− | + | for i, item in pairs(ItemData.Items) do | |
− | + | if checkFunc(item) then | |
− | + | local newItem = Shared.clone(item) | |
− | + | newItem.id = i - 1 | |
− | + | table.insert(result, newItem) | |
− | + | end | |
− | + | end | |
− | + | return result | |
end | end | ||
function p._getItemStat(item, StatName, ZeroIfNil) | function p._getItemStat(item, StatName, ZeroIfNil) | ||
− | + | local result = item[StatName] | |
− | + | --Special Overrides: | |
− | + | -- Equipment stats first | |
− | + | if Shared.contains(ItemData.EquipmentStatKeys, StatName) and item.equipmentStats ~= nil then | |
− | + | result = item.equipmentStats[StatName] | |
− | + | elseif StatName == 'isTwoHanded' then | |
− | + | if item.validSlots ~= nil and item.occupiesSlots ~= nil then | |
− | + | result = Shared.contains(item.validSlots, 'Weapon') and Shared.contains(item.occupiesSlots, 'Shield') | |
− | + | else | |
− | + | result = false | |
− | + | end | |
− | + | elseif string.find(StatName, '^(.+)LevelRequired$') ~= nil and item.equipRequirements ~= nil and item.equipRequirements.Level ~= nil then | |
− | + | local skillName = Shared.titleCase(string.match(StatName, '^(.+)LevelRequired$')) | |
− | + | if skillName ~= nil then | |
− | + | local skillID = Constants.getSkillID(skillName) | |
− | + | if skillID ~= nil then | |
− | + | result = item.equipRequirements.Level[skillID] | |
− | + | end | |
− | + | end | |
− | + | elseif StatName == 'attackType' then | |
− | + | result = p._getWeaponAttackType(item) | |
− | + | elseif StatName == 'description' then | |
− | + | result = item.description | |
− | + | if result == nil or result == '' then result = 'No Description' end | |
− | + | elseif StatName == 'completionReq' then | |
− | + | if item.ignoreCompletion == nil or not item.ignoreCompletion then | |
− | + | result = 'Yes' | |
− | + | else | |
− | + | result = 'No' | |
− | + | end | |
− | + | elseif StatName == 'slayerBonusXP' then | |
− | + | return p._getItemModifier(item, 'increasedSkillXP', 'Slayer', false) | |
− | + | elseif StatName == 'hasCombatStats' then | |
− | + | return tostring(p.hasCombatStats(item) or p._hasLevelRequirements(item)) | |
− | + | end | |
− | + | if result == nil and ZeroIfNil then result = 0 end | |
+ | return result | ||
end | end | ||
function p.getItemStat(frame) | function p.getItemStat(frame) | ||
− | + | local args = frame.args ~= nil and frame.args or frame | |
− | + | local ItemName = args[1] | |
− | + | local StatName = args[2] | |
− | + | local ZeroIfNil = args.ForceZero ~= nil and args.ForceZero ~= '' and args.ForceZero ~= 'false' | |
− | + | local formatNum = args.formatNum ~= nil and args.formatNum ~= '' and args.formatNum ~= 'false' | |
− | + | local item = p.getItem(ItemName) | |
− | + | if item == nil then | |
− | + | return "ERROR: No item named "..ItemName.." exists in the data module[[Category:Pages with script errors]]" | |
− | + | end | |
− | + | local result = p._getItemStat(item, StatName, ZeroIfNil) | |
− | + | if formatNum then result = Shared.formatnum(result) end | |
− | + | return result | |
end | end | ||
Line 163: | Line 161: | ||
--asString is false by default, when true it writes the full bonus text | --asString is false by default, when true it writes the full bonus text | ||
function p._getItemModifier(item, modifier, skill, asString) | function p._getItemModifier(item, modifier, skill, asString) | ||
− | + | if asString == nil then asString = false end | |
− | + | if skill == '' then | |
− | + | skill = nil | |
− | + | elseif type(skill) == 'string' then | |
− | + | skill = Constants.getSkillID(skill) | |
− | + | end | |
− | |||
− | |||
− | + | local result = 0 | |
− | + | if item.modifiers ~= nil and item.modifiers[modifier] ~= nil then | |
− | + | if type(item.modifiers[modifier]) == 'table' then | |
− | + | for i, subVal in Shared.skpairs(item.modifiers[modifier]) do | |
− | + | if subVal[1] == skill then | |
− | + | result = subVal[2] | |
− | + | break | |
− | + | end | |
− | + | end | |
− | + | else | |
− | + | result = item.modifiers[modifier] | |
− | + | end | |
− | + | end | |
− | + | if asString then | |
− | + | if skill ~= nil then | |
− | + | return Constants._getModifierText(modifier, {skill, result}) | |
− | + | else | |
− | + | return Constants._getModifierText(modifier, result) | |
− | + | end | |
− | + | else | |
− | + | return result | |
− | + | end | |
end | end | ||
function p.hasCombatStats(item) | function p.hasCombatStats(item) | ||
− | + | if item.isEquipment or (item.validSlots == nil and item.equipmentStats ~= nil) then | |
− | + | -- Ensure at least one stat has a non-zero value | |
− | + | for statName, statVal in pairs(item.equipmentStats) do | |
− | + | if statVal ~= 0 then return true end | |
− | + | end | |
− | + | end | |
− | + | return false | |
− | + | end | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | function p._hasLevelRequirements(item) | |
+ | --Function true if an item has at least one level requirement to equip | ||
+ | if item.equipRequirements ~= nil and item.equipRequirements.Level ~= nil then | ||
+ | for skillID, lvl in pairs(item.equipRequirements.Level) do | ||
+ | if lvl ~= nil and lvl > 1 then | ||
+ | return true | ||
+ | end | ||
+ | end | ||
+ | return false | ||
+ | else | ||
+ | return false | ||
+ | end | ||
end | end | ||
function p.getItemModifier(frame) | function p.getItemModifier(frame) | ||
− | + | local itemName = frame.args ~= nil and frame.args[1] or frame[1] | |
− | + | local modName = frame.args ~= nil and frame.args[2] or frame[2] | |
− | + | local skillName = frame.args ~= nil and frame.args[3] or frame[3] | |
− | + | local asString = frame.args ~= nil and frame.args[4] or frame[4] | |
− | + | if asString ~= nil then | |
− | + | asString = (string.upper(asString) ~= 'FALSE') | |
− | + | end | |
− | |||
− | |||
− | |||
− | |||
− | + | local item = p.getItem(itemName) | |
− | + | if item == nil then | |
− | + | return "ERROR: No item named "..itemName.." exists in the data module[[Category:Pages with script errors]]" | |
− | + | end | |
− | + | return p._getItemModifier(item, modName, skillName, asString) | |
end | end | ||
function p._getWeaponAttackType(item) | function p._getWeaponAttackType(item) | ||
− | + | if item.isEquipment == true and (item.validSlots ~= nil and Shared.contains(item.validSlots, 'Weapon')) or | |
− | + | (item.occupiesSlots ~= nil and Shared.contains(item.occupiesSlots, 'Weapon')) then | |
− | + | if Shared.contains({'melee', 'ranged', 'magic'}, item.attackType) then | |
− | + | local iconType = item.attackType ~= 'melee' and 'skill' or nil | |
− | + | return Icons.Icon({Shared.titleCase(item.attackType), type=iconType, nolink='true'}) | |
− | + | end | |
− | + | end | |
− | + | return 'Invalid' | |
− | |||
end | end | ||
− | |||
function p.getWeaponAttackType(frame) | function p.getWeaponAttackType(frame) | ||
− | + | local itemName = frame.args ~= nil and frame.args[1] or frame | |
− | + | local item = p.getItem(itemName) | |
− | + | if item == nil then | |
− | + | return "ERROR: No item named "..ItemName.." exists in the data module[[Category:Pages with script errors]]" | |
− | + | end | |
− | + | return p._getWeaponAttackType(item) | |
end | end | ||
function p.getPotionTable(frame) | function p.getPotionTable(frame) | ||
− | + | local potionName = frame.args ~= nil and frame.args[1] or frame | |
− | + | local tiers = {'I', 'II', 'III', 'IV'} | |
− | + | local resultPart = {} | |
− | + | table.insert(resultPart, '{| class="wikitable"') | |
+ | table.insert(resultPart, '\r\n!Potion!!Tier!!Charges!!Effect') | ||
− | + | local tier1potion = p.getItem(potionName..' I') | |
− | + | if tier1potion == nil then | |
− | + | return 'ERROR: No potion named "' .. potionName .. '" was found[[Category:Pages with script errors]]' | |
− | + | end | |
− | + | for i, tier in pairs(tiers) do | |
− | + | local tierName = potionName..' '..tier | |
− | + | local potion = p.getItemByID(tier1potion.id + i - 1) | |
− | + | if potion ~= nil then | |
− | + | table.insert(resultPart, '\r\n|-') | |
− | + | table.insert(resultPart, '\r\n|'..Icons.Icon({tierName, type='item', notext=true, size='60'})) | |
− | + | table.insert(resultPart, '||'..Icons.Icon({tierName, tier, type='item', noicon=true})) | |
+ | table.insert(resultPart, '||'..potion.potionCharges..'||'..potion.description) | ||
+ | end | ||
+ | end | ||
− | + | table.insert(resultPart, '\r\n|}') | |
− | + | return table.concat(resultPart) | |
end | end | ||
function p._getOtherItemBoxText(item) | function p._getOtherItemBoxText(item) | ||
− | + | resultPart = {} | |
− | + | --For equipment, show the slot they go in | |
− | + | if item.validSlots ~= nil then | |
− | + | local slotLinkMap = { | |
− | + | ["Helmet"] = 'Equipment#Helmets', | |
− | + | ["Platebody"] = 'Equipment#Platebodies', | |
− | + | ["Boots"] = 'Equipment#Boots', | |
− | + | ["Weapon"] = 'Equipment#Weapons', | |
− | + | ["Shield"] = 'Equipment#Offhand', | |
− | + | ["Amulet"] = 'Equipment#Amulets', | |
− | + | ["Ring"] = 'Equipment#Rings', | |
− | + | ["Gloves"] = 'Equipment#Gloves', | |
− | + | ["Quiver"] = 'Equipment#Ammunition', | |
− | + | ["Cape"] = 'Equipment#Capes', | |
− | + | ["Passive"] = 'Combat Passive Slot', | |
− | + | ["Summon1"] = 'Summoning', | |
− | + | ["Summon2"] = 'Summoning' | |
− | + | } | |
− | + | local slotText = {} | |
− | + | for i, slot in ipairs(item.validSlots) do | |
− | + | local slotLink = slotLinkMap[slot] | |
− | + | if slotLink == nil then | |
− | + | table.insert(slotText, slot) | |
− | + | else | |
− | + | table.insert(slotText, '[[' .. slotLink .. '|' .. slot .. ']]') | |
− | + | end | |
− | + | end | |
− | + | table.insert(resultPart, "\r\n|-\r\n|'''Equipment Slot:''' "..table.concat(slotText, ', ')) | |
− | + | end | |
− | + | --For weapons with a special attack, show the details | |
− | + | if item.hasSpecialAttack then | |
− | + | table.insert(resultPart, "\r\n|-\r\n|'''Special Attack:'''") | |
+ | for i, spAtt in ipairs(item.specialAttacks) do | ||
+ | table.insert(resultPart, '\r\n* ' .. spAtt.defaultChance .. '% chance for ' .. spAtt.name .. ':') | ||
+ | table.insert(resultPart, '\r\n** ' .. spAtt.description) | ||
+ | end | ||
+ | end | ||
+ | --For potions, show the number of charges | ||
+ | if item.potionCharges ~= nil then | ||
+ | table.insert(resultPart, "\r\n|-\r\n|'''Charges:''' "..item.potionCharges) | ||
+ | end | ||
+ | --For food, show how much it heals for | ||
+ | if item.healsFor ~= nil then | ||
+ | table.insert(resultPart, "\r\n|-\r\n|'''Heals for:''' "..Icons.Icon({"Hitpoints", type="skill", notext="true"})..' '..(item.healsFor * 10)) | ||
+ | end | ||
+ | --For Prayer Points, show how many you get | ||
+ | if item.prayerPoints ~= nil then | ||
+ | table.insert(resultPart, "\r\n|-\r\n|'''"..Icons.Icon({'Prayer', type='skill'}).." Points:''' "..item.prayerPoints) | ||
+ | end | ||
+ | --For items with modifiers, show what those are | ||
+ | if item.modifiers ~= nil and Shared.tableCount(item.modifiers) > 0 then | ||
+ | table.insert(resultPart, "\r\n|-\r\n|'''Modifiers:'''\r\n"..Constants.getModifiersText(item.modifiers, true)) | ||
+ | end | ||
+ | return table.concat(resultPart) | ||
end | end | ||
function p.getOtherItemBoxText(frame) | function p.getOtherItemBoxText(frame) | ||
− | + | local itemName = frame.args ~= nil and frame.args[1] or frame | |
− | + | local item = p.getItem(itemName) | |
− | + | local asList = false | |
− | + | if frame.args ~= nil then | |
− | + | asList = frame.args.asList ~= nil and frame.args.asList ~= '' and frame.args.asList ~= 'false' | |
− | + | end | |
− | + | if item == nil then | |
− | + | return "ERROR: No item named "..itemName.." exists in the data module[[Category:Pages with script errors]]" | |
− | + | end | |
− | + | return p._getOtherItemBoxText(item, asList) | |
end | end | ||
function p._getItemCategories(item) | function p._getItemCategories(item) | ||
− | + | local resultPart = {} | |
− | + | if item.category ~= nil then table.insert(resultPart, '[[Category:'..item.category..']]') end | |
− | + | if item.type ~= nil then table.insert(resultPart, '[[Category:'..item.type..']]') end | |
− | + | if item.tier ~= nil then table.insert(resultPart, '[[Category:'..Shared.titleCase(item.tier)..' '..item.type..']]') end | |
− | + | if item.hasSpecialAttack then table.insert(resultPart, '[[Category:Items With Special Attacks]]') end | |
− | + | if item.validSlots ~= nil then | |
− | + | local slotRemap = { | |
− | + | ['Passive'] = 'Passive Items', | |
+ | ['Summon1'] = 'Summoning Familiars', | ||
+ | ['Summon2'] = '' | ||
+ | } | ||
+ | for i, slotName in ipairs(item.validSlots) do | ||
+ | local slotRemapName = slotName | ||
+ | if slotRemap[slotName] ~= nil then slotRemapName = slotRemap[slotName] end | ||
+ | if slotRemapName ~= '' then table.insert(resultPart, '[[Category:' .. slotRemapName .. ']]') end | ||
+ | end | ||
+ | end | ||
+ | if item.modifiers ~= nil then | ||
+ | local modsDL = { | ||
+ | 'increasedChanceToDoubleLootCombat', | ||
+ | 'decreasedChanceToDoubleLootCombat', | ||
+ | 'increasedChanceToDoubleLootThieving', | ||
+ | 'decreasedChanceToDoubleLootThieving', | ||
+ | 'increasedChanceToDoubleItemsGlobal', | ||
+ | 'decreasedChanceToDoubleItemsGlobal' | ||
+ | } | ||
+ | for modName, val in pairs(item.modifiers) do | ||
+ | if Shared.contains(modsDL, modName) then | ||
+ | table.insert(resultPart, '[[Category:Double Loot Chance Items]]') | ||
+ | break | ||
+ | end | ||
+ | end | ||
+ | end | ||
+ | return table.concat(resultPart) | ||
end | end | ||
function p.getItemCategories(frame) | function p.getItemCategories(frame) | ||
− | + | local itemName = frame.args ~= nil and frame.args[1] or frame | |
− | + | local item = p.getItem(itemName) | |
− | + | if item == nil then | |
− | + | return "ERROR: No item named "..itemName.." exists in the data module[[Category:Pages with script errors]]" | |
− | + | end | |
− | + | return p._getItemCategories(item) | |
end | end | ||
function p.getSkillcapeTable(frame) | function p.getSkillcapeTable(frame) | ||
− | + | local skillName = frame.args ~= nil and frame.args[1] or frame | |
− | + | local cape = p.getItem(skillName..' Skillcape') | |
− | + | local resultPart = {} | |
− | + | table.insert(resultPart, '{| class="wikitable"\r\n') | |
− | + | table.insert(resultPart, '!Skillcape!!Name!!Effect') | |
− | + | table.insert(resultPart, '\r\n|-\r\n|'..Icons.Icon({cape.name, type='item', size='60', notext=true})) | |
− | + | table.insert(resultPart, '||'..Icons.Icon({cape.name, type='item', noicon=true})..'||'..cape.description) | |
− | + | table.insert(resultPart, '\r\n|}') | |
+ | return table.concat(resultPart) | ||
end | end | ||
− | function p. | + | function p.getItemGrid(frame) |
− | + | local resultPart = {} | |
+ | table.insert(resultPart, '{|') | ||
+ | for i, item in Shared.skpairs(ItemData.Items) do | ||
+ | if i % 17 == 1 then | ||
+ | table.insert(resultPart, '\r\n|-\r\n|') | ||
+ | else | ||
+ | table.insert(resultPart, '||') | ||
+ | end | ||
+ | table.insert(resultPart, 'style="padding:3px"|'..Icons.Icon({item.name, type='item', notext=true, size='40'})) | ||
+ | end | ||
+ | table.insert(resultPart, '\r\n|}') | ||
+ | return table.concat(resultPart) | ||
+ | end | ||
− | + | function p.getSpecialAttackTable(frame) | |
− | + | local spAttTable = {} | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | for i, item in Shared.skpairs(ItemData.Items) do | |
− | + | if item.hasSpecialAttack then | |
− | + | for i, spAtt in ipairs(item.specialAttacks) do | |
− | + | if spAttTable[spAtt.id] == nil then spAttTable[spAtt.id] = {sortName=item.name, defn = spAtt, Icons = {}} end | |
− | + | table.insert(spAttTable[spAtt.id].Icons, Icons.Icon({item.name, type='item'})) | |
− | + | end | |
− | + | end | |
− | + | end | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | local resultPart = {} | |
− | end | + | table.insert(resultPart, '{|class="wikitable sortable stickyHeader"') |
+ | table.insert(resultPart, '\r\n|-class="headerRow-0"') | ||
+ | table.insert(resultPart, '\r\n!style="min-width:180px"|Weapon(s)!!Name!!Chance!!Effect') | ||
+ | for i, spAttData in Shared.skpairs(spAttTable) do | ||
+ | local spAtt = spAttData.defn | ||
+ | table.sort(spAttData.Icons, function(a, b) return a < b end) | ||
+ | table.insert(resultPart, '\r\n|-') | ||
+ | table.insert(resultPart, '\r\n|data-sort-value="'..spAttData.sortName..'"|'..table.concat(spAttData.Icons, '<br/>')) | ||
+ | table.insert(resultPart, '||'..spAtt.name..'||data-sort-value="'..spAtt.defaultChance..'"|'..spAtt.defaultChance..'%') | ||
+ | table.insert(resultPart, '||'..spAtt.description) | ||
+ | end | ||
+ | table.insert(resultPart, '\r\n|}') | ||
− | + | return table.concat(resultPart) | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
end | end | ||
− | function p. | + | function p.getWeaponStatsBox(frame) |
− | + | local itemName = frame.args ~= nil and frame.args[1] or frame | |
− | + | local item = p.getItem(itemName) | |
− | + | if item == nil then | |
− | + | return "ERROR: No item named "..itemName.." exists in the data module[[Category:Pages with script errors]]" | |
− | + | end | |
− | + | ||
− | + | local ico = { | |
− | + | ["Attack"] = Icons.Icon({'Attack', type='skill', notext=true}), | |
− | + | ["Combat"] = Icons.Icon({'Combat', notext=true}), | |
− | + | ["Defence"] = Icons.Icon({'Defence', type='skill', notext=true}), | |
− | + | ["Magic"] = Icons.Icon({'Magic', type='skill', notext=true}), | |
− | + | ["Ranged"] = Icons.Icon({'Ranged', type='skill', notext=true}), | |
− | + | ["Strength"] = Icons.Icon({'Strength', type='skill', notext=true}), | |
− | + | ["Slayer"] = Icons.Icon({'Slayer', type='skill', notext=true}) | |
− | + | } | |
− | + | local resultPart = {} | |
− | + | table.insert(resultPart, '{| class="wikitable"\r\n|-\r\n!colspan="4" style="border-bottom:solid medium black;"| Weapon Stats') | |
− | + | table.insert(resultPart, '\r\n|-\r\n!colspan="2" style="border-bottom:solid thin black;"| Offensive Stats') | |
− | + | table.insert(resultPart, '\r\n!colspan="2" style="border-bottom:solid thin black;"| Defensive Stats') | |
− | + | ||
− | + | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| Attack Speed') | |
− | + | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. Shared.round(p._getItemStat(item, 'attackSpeed', true) / 1000, 3, 1) .. 's') | |
− | + | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Defence'] .. ' Defence Bonus') | |
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'meleeDefenceBonus', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| Attack Type') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'attackType')) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Defence'] .. ' Damage Reduction') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'damageReduction', true) .. '%') | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Strength'] .. ' Strength Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'meleeStrengthBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Defence Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedDefenceBonus', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Stab Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'stabAttackBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;border-bottom:solid thin black;"| ' .. ico['Magic'] .. ' Defence Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;border-bottom:solid thin black;"| ' .. p._getItemStat(item, 'magicDefenceBonus', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Slash Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'slashAttackBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!colspan="2" style="border-bottom:solid thin black;"| Other') | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Block Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'blockAttackBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Slayer'] .. ' Bonus Slayer XP') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'slayerBonusXP', true) .. '%') | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Attack Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedAttackBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Attack'] .. ' Level Required') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'attackLevelRequired', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Strength Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedStrengthBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Level Required') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedLevelRequired', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' Attack Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicAttackBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' Level Required') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicLevelRequired', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' % Damage Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicDamageBonus', true) .. '%') | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| Two Handed?') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. (p._getItemStat(item, 'isTwoHanded') and 'Yes' or 'No')) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|}') | ||
+ | return table.concat(resultPart) | ||
end | end | ||
− | function p. | + | function p.getArmourStatsBox(frame) |
− | + | local itemName = frame.args ~= nil and frame.args[1] or frame | |
− | + | local item = p.getItem(itemName) | |
− | + | if item == nil then | |
− | + | return "ERROR: No item named "..itemName.." exists in the data module[[Category:Pages with script errors]]" | |
− | + | end | |
− | + | ||
− | + | local ico = { | |
− | + | ["Attack"] = Icons.Icon({'Attack', type='skill', notext=true}), | |
− | + | ["Combat"] = Icons.Icon({'Combat', notext=true}), | |
− | + | ["Defence"] = Icons.Icon({'Defence', type='skill', notext=true}), | |
− | + | ["Magic"] = Icons.Icon({'Magic', type='skill', notext=true}), | |
− | + | ["Ranged"] = Icons.Icon({'Ranged', type='skill', notext=true}), | |
− | + | ["Strength"] = Icons.Icon({'Strength', type='skill', notext=true}), | |
− | + | ["Slayer"] = Icons.Icon({'Slayer', type='skill', notext=true}) | |
− | + | } | |
− | + | local resultPart = {} | |
− | + | table.insert(resultPart, '{| class="wikitable"\r\n|-\r\n!colspan="4" style="border-bottom:solid medium black;"| Armour Stats') | |
− | + | table.insert(resultPart, '\r\n|-\r\n!colspan="2" style="border-bottom:solid thin black;"| Offensive Stats') | |
− | + | table.insert(resultPart, '\r\n!colspan="2" style="border-bottom:solid thin black;"| Defensive Stats') | |
− | + | ||
− | + | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Strength'] .. ' Strength Bonus') | |
− | + | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'meleeStrengthBonus', true)) | |
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Defence'] .. ' Defence Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'meleeDefenceBonus', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Stab Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'stabAttackBonus', 0)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Defence'] .. ' Damage Reduction') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'damageReduction', true) .. '%') | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Slash Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'slashAttackBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Defence Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedDefenceBonus', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Block Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'blockAttackBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;border-bottom:solid thin black;"| ' .. ico['Magic'] .. ' Defence Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;border-bottom:solid thin black;"| ' .. p._getItemStat(item, 'magicDefenceBonus', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Attack Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedAttackBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!colspan="2" style="border-bottom:solid thin black;"| Other') | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Strength Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedStrengthBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Slayer'] .. ' Bonus Slayer XP') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'slayerBonusXP', true) .. '%') | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' Attack Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicAttackBonus', true)) | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Defence'] .. ' Level Required') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'defenceLevelRequired', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' % Damage Bonus') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicDamageBonus', true) .. '%') | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Level Required') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedLevelRequired', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|-\r\n| colspan="2"|') | ||
+ | table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' Level Required') | ||
+ | table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicLevelRequired', true)) | ||
+ | |||
+ | table.insert(resultPart, '\r\n|}') | ||
+ | return table.concat(resultPart) | ||
end | end | ||
return p | return p |
Revision as of 00:45, 12 January 2022
Lua module for generating various item tables. Pulls data from Module:Items/data
--This module contains all sorts of functions for getting data on items --Several functions related to use tables can be found at Module:Items/UseTables --Functions related to source tables can be found at Module:Items/SourceTables --Other functions moved to Module:Items/ComparisonTables local p = {} local ItemData = mw.loadData('Module:Items/data') local Constants = require('Module:Constants') local Shared = require('Module:Shared') local Icons = require('Module:Icons') p.EasterEggs = {'Amulet of Calculated Promotion', 'Clue Chasers Insignia', '8', 'Lemon', 'Easter Egg', 'Abnormal Log', 'Red Herring', 'Cool Glasses'} p.EventItems = {'Christmas Cracker', 'Christmas Coal', 'Christmas Sweater', 'Christmas Wreath', 'Candy Cane', 'Santa Hat', 'Friendship Bracelet', 'Event Clue 1', 'Event Clue 2', 'Event Clue 3', 'Event Clue 4', 'Candle', 'Cake Base', 'Magical Flavouring', 'Magical Icing', 'Birthday Cake', 'Purple Party Hat', 'Birthday Token', 'Christmas Present (Yellow)', 'Christmas Present (Blue)', 'Christmas Present (Green)', 'Christmas Present (White)', 'Christmas Present (Purple)', 'Christmas Present (Standard)', 'Event Token - Holiday 2021', 'Holiday Scarf', 'Gingerbread House', 'Gingerbread Man', 'Edible Candy Cane', 'Locked Chest', 'Locked Chest Key', 'Event Token (Holiday 2021)'} p.OtherShopItems = {'Cooking Gloves', 'Mining Gloves', 'Gem Gloves', 'Smithing Gloves', 'Thieving Gloves'} --This is hardcoded, so there's no easy way to scrape it. Hopefully it doesn't change p.GemTable = {["Topaz"] = {name = 'Topaz', id = 128, chance = 50}, ["Sapphire"] = {name = "Sapphire", id = 129, chance = 17.5}, ["Ruby"] = {name = "Ruby", id = 130, chance = 17.5}, ["Emerald"] = {name = "Emerald", id = 131, chance = 10}, ["Diamond"] = {name = "Diamond", id = 132, chance = 5}} --The base chance to receive a gem while mining p.GemChance = .01 --The number of different fishing junk items p.junkCount = 8 --Items (aside from bars & gems) which can be created via Alt Magic p.AltMagicProducts = {'Rune Essence', 'Bones', 'Holy Dust'} --The kinds of gloves with cost & charges p.GloveTable = {['Cooking Gloves'] = {cost=50000, charges=500}, ['Mining Gloves'] = {cost=75000, charges=500}, ['Smithing Gloves'] = {cost=100000, charges=500}, ['Thieving Gloves'] = {cost=100000, charges=500}, ['Gem Gloves'] = {cost=500000, charges=2000}} p.specialFishWt = 6722 p.specialFishLoot = {{128, 2000}, {129, 1600}, {130, 1400}, {131, 1000}, {132, 400}, {667, 10}, {668, 10}, {902, 1}, {670, 1}, {669, 50}, {120, 250}} function p.buildSpecialFishingTable() --This shouldn't ever be included in a page --This is for generating the above 'specialFishLoot' variable if it ever needs to change --To re-run, edit the module, type in "console.log(p.buildSpecialFishingTable())" and copy+paste the result as the new value of the variable --Also gives you the total fishing weight for saving time later local lootArray = {} local totalWt = 0 for i, item in pairs(ItemData.Items) do if item.fishingCatchWeight ~= nil then totalWt = totalWt + item.fishingCatchWeight table.insert(lootArray, '{'..(i - 1)..', '..item.fishingCatchWeight..'}') end end local result = 'p.specialFishWt = '..totalWt..'\r\n' result = result..'p.specialFishLoot = {'..table.concat(lootArray, ', ')..'}' return result end function p.getItemByID(ID) local result = Shared.clone(ItemData.Items[ID + 1]) if result ~= nil then result.id = ID end return result end function p.getItem(name) local result = nil name = string.gsub(name, "%%27", "'") name = string.gsub(name, "'", "'") for i, item in pairs(ItemData.Items) do local itemName = string.gsub(item.name, '#', '') if name == itemName then result = Shared.clone(item) --Make sure every item has an id, and account for Lua being 1-index result.id = i - 1 break end end return result end function p.getItems(checkFunc) local result = {} for i, item in pairs(ItemData.Items) do if checkFunc(item) then local newItem = Shared.clone(item) newItem.id = i - 1 table.insert(result, newItem) end end return result end function p._getItemStat(item, StatName, ZeroIfNil) local result = item[StatName] --Special Overrides: -- Equipment stats first if Shared.contains(ItemData.EquipmentStatKeys, StatName) and item.equipmentStats ~= nil then result = item.equipmentStats[StatName] elseif StatName == 'isTwoHanded' then if item.validSlots ~= nil and item.occupiesSlots ~= nil then result = Shared.contains(item.validSlots, 'Weapon') and Shared.contains(item.occupiesSlots, 'Shield') else result = false end elseif string.find(StatName, '^(.+)LevelRequired$') ~= nil and item.equipRequirements ~= nil and item.equipRequirements.Level ~= nil then local skillName = Shared.titleCase(string.match(StatName, '^(.+)LevelRequired$')) if skillName ~= nil then local skillID = Constants.getSkillID(skillName) if skillID ~= nil then result = item.equipRequirements.Level[skillID] end end elseif StatName == 'attackType' then result = p._getWeaponAttackType(item) elseif StatName == 'description' then result = item.description if result == nil or result == '' then result = 'No Description' end elseif StatName == 'completionReq' then if item.ignoreCompletion == nil or not item.ignoreCompletion then result = 'Yes' else result = 'No' end elseif StatName == 'slayerBonusXP' then return p._getItemModifier(item, 'increasedSkillXP', 'Slayer', false) elseif StatName == 'hasCombatStats' then return tostring(p.hasCombatStats(item) or p._hasLevelRequirements(item)) end if result == nil and ZeroIfNil then result = 0 end return result end function p.getItemStat(frame) local args = frame.args ~= nil and frame.args or frame local ItemName = args[1] local StatName = args[2] local ZeroIfNil = args.ForceZero ~= nil and args.ForceZero ~= '' and args.ForceZero ~= 'false' local formatNum = args.formatNum ~= nil and args.formatNum ~= '' and args.formatNum ~= 'false' local item = p.getItem(ItemName) if item == nil then return "ERROR: No item named "..ItemName.." exists in the data module[[Category:Pages with script errors]]" end local result = p._getItemStat(item, StatName, ZeroIfNil) if formatNum then result = Shared.formatnum(result) end return result end --Gets the value of a given modifier for a given item --asString is false by default, when true it writes the full bonus text function p._getItemModifier(item, modifier, skill, asString) if asString == nil then asString = false end if skill == '' then skill = nil elseif type(skill) == 'string' then skill = Constants.getSkillID(skill) end local result = 0 if item.modifiers ~= nil and item.modifiers[modifier] ~= nil then if type(item.modifiers[modifier]) == 'table' then for i, subVal in Shared.skpairs(item.modifiers[modifier]) do if subVal[1] == skill then result = subVal[2] break end end else result = item.modifiers[modifier] end end if asString then if skill ~= nil then return Constants._getModifierText(modifier, {skill, result}) else return Constants._getModifierText(modifier, result) end else return result end end function p.hasCombatStats(item) if item.isEquipment or (item.validSlots == nil and item.equipmentStats ~= nil) then -- Ensure at least one stat has a non-zero value for statName, statVal in pairs(item.equipmentStats) do if statVal ~= 0 then return true end end end return false end function p._hasLevelRequirements(item) --Function true if an item has at least one level requirement to equip if item.equipRequirements ~= nil and item.equipRequirements.Level ~= nil then for skillID, lvl in pairs(item.equipRequirements.Level) do if lvl ~= nil and lvl > 1 then return true end end return false else return false end end function p.getItemModifier(frame) local itemName = frame.args ~= nil and frame.args[1] or frame[1] local modName = frame.args ~= nil and frame.args[2] or frame[2] local skillName = frame.args ~= nil and frame.args[3] or frame[3] local asString = frame.args ~= nil and frame.args[4] or frame[4] if asString ~= nil then asString = (string.upper(asString) ~= 'FALSE') end local item = p.getItem(itemName) if item == nil then return "ERROR: No item named "..itemName.." exists in the data module[[Category:Pages with script errors]]" end return p._getItemModifier(item, modName, skillName, asString) end function p._getWeaponAttackType(item) if item.isEquipment == true and (item.validSlots ~= nil and Shared.contains(item.validSlots, 'Weapon')) or (item.occupiesSlots ~= nil and Shared.contains(item.occupiesSlots, 'Weapon')) then if Shared.contains({'melee', 'ranged', 'magic'}, item.attackType) then local iconType = item.attackType ~= 'melee' and 'skill' or nil return Icons.Icon({Shared.titleCase(item.attackType), type=iconType, nolink='true'}) end end return 'Invalid' end function p.getWeaponAttackType(frame) local itemName = frame.args ~= nil and frame.args[1] or frame local item = p.getItem(itemName) if item == nil then return "ERROR: No item named "..ItemName.." exists in the data module[[Category:Pages with script errors]]" end return p._getWeaponAttackType(item) end function p.getPotionTable(frame) local potionName = frame.args ~= nil and frame.args[1] or frame local tiers = {'I', 'II', 'III', 'IV'} local resultPart = {} table.insert(resultPart, '{| class="wikitable"') table.insert(resultPart, '\r\n!Potion!!Tier!!Charges!!Effect') local tier1potion = p.getItem(potionName..' I') if tier1potion == nil then return 'ERROR: No potion named "' .. potionName .. '" was found[[Category:Pages with script errors]]' end for i, tier in pairs(tiers) do local tierName = potionName..' '..tier local potion = p.getItemByID(tier1potion.id + i - 1) if potion ~= nil then table.insert(resultPart, '\r\n|-') table.insert(resultPart, '\r\n|'..Icons.Icon({tierName, type='item', notext=true, size='60'})) table.insert(resultPart, '||'..Icons.Icon({tierName, tier, type='item', noicon=true})) table.insert(resultPart, '||'..potion.potionCharges..'||'..potion.description) end end table.insert(resultPart, '\r\n|}') return table.concat(resultPart) end function p._getOtherItemBoxText(item) resultPart = {} --For equipment, show the slot they go in if item.validSlots ~= nil then local slotLinkMap = { ["Helmet"] = 'Equipment#Helmets', ["Platebody"] = 'Equipment#Platebodies', ["Boots"] = 'Equipment#Boots', ["Weapon"] = 'Equipment#Weapons', ["Shield"] = 'Equipment#Offhand', ["Amulet"] = 'Equipment#Amulets', ["Ring"] = 'Equipment#Rings', ["Gloves"] = 'Equipment#Gloves', ["Quiver"] = 'Equipment#Ammunition', ["Cape"] = 'Equipment#Capes', ["Passive"] = 'Combat Passive Slot', ["Summon1"] = 'Summoning', ["Summon2"] = 'Summoning' } local slotText = {} for i, slot in ipairs(item.validSlots) do local slotLink = slotLinkMap[slot] if slotLink == nil then table.insert(slotText, slot) else table.insert(slotText, '[[' .. slotLink .. '|' .. slot .. ']]') end end table.insert(resultPart, "\r\n|-\r\n|'''Equipment Slot:''' "..table.concat(slotText, ', ')) end --For weapons with a special attack, show the details if item.hasSpecialAttack then table.insert(resultPart, "\r\n|-\r\n|'''Special Attack:'''") for i, spAtt in ipairs(item.specialAttacks) do table.insert(resultPart, '\r\n* ' .. spAtt.defaultChance .. '% chance for ' .. spAtt.name .. ':') table.insert(resultPart, '\r\n** ' .. spAtt.description) end end --For potions, show the number of charges if item.potionCharges ~= nil then table.insert(resultPart, "\r\n|-\r\n|'''Charges:''' "..item.potionCharges) end --For food, show how much it heals for if item.healsFor ~= nil then table.insert(resultPart, "\r\n|-\r\n|'''Heals for:''' "..Icons.Icon({"Hitpoints", type="skill", notext="true"})..' '..(item.healsFor * 10)) end --For Prayer Points, show how many you get if item.prayerPoints ~= nil then table.insert(resultPart, "\r\n|-\r\n|'''"..Icons.Icon({'Prayer', type='skill'}).." Points:''' "..item.prayerPoints) end --For items with modifiers, show what those are if item.modifiers ~= nil and Shared.tableCount(item.modifiers) > 0 then table.insert(resultPart, "\r\n|-\r\n|'''Modifiers:'''\r\n"..Constants.getModifiersText(item.modifiers, true)) end return table.concat(resultPart) end function p.getOtherItemBoxText(frame) local itemName = frame.args ~= nil and frame.args[1] or frame local item = p.getItem(itemName) local asList = false if frame.args ~= nil then asList = frame.args.asList ~= nil and frame.args.asList ~= '' and frame.args.asList ~= 'false' end if item == nil then return "ERROR: No item named "..itemName.." exists in the data module[[Category:Pages with script errors]]" end return p._getOtherItemBoxText(item, asList) end function p._getItemCategories(item) local resultPart = {} if item.category ~= nil then table.insert(resultPart, '[[Category:'..item.category..']]') end if item.type ~= nil then table.insert(resultPart, '[[Category:'..item.type..']]') end if item.tier ~= nil then table.insert(resultPart, '[[Category:'..Shared.titleCase(item.tier)..' '..item.type..']]') end if item.hasSpecialAttack then table.insert(resultPart, '[[Category:Items With Special Attacks]]') end if item.validSlots ~= nil then local slotRemap = { ['Passive'] = 'Passive Items', ['Summon1'] = 'Summoning Familiars', ['Summon2'] = '' } for i, slotName in ipairs(item.validSlots) do local slotRemapName = slotName if slotRemap[slotName] ~= nil then slotRemapName = slotRemap[slotName] end if slotRemapName ~= '' then table.insert(resultPart, '[[Category:' .. slotRemapName .. ']]') end end end if item.modifiers ~= nil then local modsDL = { 'increasedChanceToDoubleLootCombat', 'decreasedChanceToDoubleLootCombat', 'increasedChanceToDoubleLootThieving', 'decreasedChanceToDoubleLootThieving', 'increasedChanceToDoubleItemsGlobal', 'decreasedChanceToDoubleItemsGlobal' } for modName, val in pairs(item.modifiers) do if Shared.contains(modsDL, modName) then table.insert(resultPart, '[[Category:Double Loot Chance Items]]') break end end end return table.concat(resultPart) end function p.getItemCategories(frame) local itemName = frame.args ~= nil and frame.args[1] or frame local item = p.getItem(itemName) if item == nil then return "ERROR: No item named "..itemName.." exists in the data module[[Category:Pages with script errors]]" end return p._getItemCategories(item) end function p.getSkillcapeTable(frame) local skillName = frame.args ~= nil and frame.args[1] or frame local cape = p.getItem(skillName..' Skillcape') local resultPart = {} table.insert(resultPart, '{| class="wikitable"\r\n') table.insert(resultPart, '!Skillcape!!Name!!Effect') table.insert(resultPart, '\r\n|-\r\n|'..Icons.Icon({cape.name, type='item', size='60', notext=true})) table.insert(resultPart, '||'..Icons.Icon({cape.name, type='item', noicon=true})..'||'..cape.description) table.insert(resultPart, '\r\n|}') return table.concat(resultPart) end function p.getItemGrid(frame) local resultPart = {} table.insert(resultPart, '{|') for i, item in Shared.skpairs(ItemData.Items) do if i % 17 == 1 then table.insert(resultPart, '\r\n|-\r\n|') else table.insert(resultPart, '||') end table.insert(resultPart, 'style="padding:3px"|'..Icons.Icon({item.name, type='item', notext=true, size='40'})) end table.insert(resultPart, '\r\n|}') return table.concat(resultPart) end function p.getSpecialAttackTable(frame) local spAttTable = {} for i, item in Shared.skpairs(ItemData.Items) do if item.hasSpecialAttack then for i, spAtt in ipairs(item.specialAttacks) do if spAttTable[spAtt.id] == nil then spAttTable[spAtt.id] = {sortName=item.name, defn = spAtt, Icons = {}} end table.insert(spAttTable[spAtt.id].Icons, Icons.Icon({item.name, type='item'})) end end end local resultPart = {} table.insert(resultPart, '{|class="wikitable sortable stickyHeader"') table.insert(resultPart, '\r\n|-class="headerRow-0"') table.insert(resultPart, '\r\n!style="min-width:180px"|Weapon(s)!!Name!!Chance!!Effect') for i, spAttData in Shared.skpairs(spAttTable) do local spAtt = spAttData.defn table.sort(spAttData.Icons, function(a, b) return a < b end) table.insert(resultPart, '\r\n|-') table.insert(resultPart, '\r\n|data-sort-value="'..spAttData.sortName..'"|'..table.concat(spAttData.Icons, '<br/>')) table.insert(resultPart, '||'..spAtt.name..'||data-sort-value="'..spAtt.defaultChance..'"|'..spAtt.defaultChance..'%') table.insert(resultPart, '||'..spAtt.description) end table.insert(resultPart, '\r\n|}') return table.concat(resultPart) end function p.getWeaponStatsBox(frame) local itemName = frame.args ~= nil and frame.args[1] or frame local item = p.getItem(itemName) if item == nil then return "ERROR: No item named "..itemName.." exists in the data module[[Category:Pages with script errors]]" end local ico = { ["Attack"] = Icons.Icon({'Attack', type='skill', notext=true}), ["Combat"] = Icons.Icon({'Combat', notext=true}), ["Defence"] = Icons.Icon({'Defence', type='skill', notext=true}), ["Magic"] = Icons.Icon({'Magic', type='skill', notext=true}), ["Ranged"] = Icons.Icon({'Ranged', type='skill', notext=true}), ["Strength"] = Icons.Icon({'Strength', type='skill', notext=true}), ["Slayer"] = Icons.Icon({'Slayer', type='skill', notext=true}) } local resultPart = {} table.insert(resultPart, '{| class="wikitable"\r\n|-\r\n!colspan="4" style="border-bottom:solid medium black;"| Weapon Stats') table.insert(resultPart, '\r\n|-\r\n!colspan="2" style="border-bottom:solid thin black;"| Offensive Stats') table.insert(resultPart, '\r\n!colspan="2" style="border-bottom:solid thin black;"| Defensive Stats') table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| Attack Speed') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. Shared.round(p._getItemStat(item, 'attackSpeed', true) / 1000, 3, 1) .. 's') table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Defence'] .. ' Defence Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'meleeDefenceBonus', true)) table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| Attack Type') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'attackType')) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Defence'] .. ' Damage Reduction') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'damageReduction', true) .. '%') table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Strength'] .. ' Strength Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'meleeStrengthBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Defence Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedDefenceBonus', true)) table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Stab Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'stabAttackBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;border-bottom:solid thin black;"| ' .. ico['Magic'] .. ' Defence Bonus') table.insert(resultPart, '\r\n|style="text-align:right;border-bottom:solid thin black;"| ' .. p._getItemStat(item, 'magicDefenceBonus', true)) table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Slash Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'slashAttackBonus', true)) table.insert(resultPart, '\r\n!colspan="2" style="border-bottom:solid thin black;"| Other') table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Block Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'blockAttackBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Slayer'] .. ' Bonus Slayer XP') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'slayerBonusXP', true) .. '%') table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Attack Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedAttackBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Attack'] .. ' Level Required') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'attackLevelRequired', true)) table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Strength Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedStrengthBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Level Required') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedLevelRequired', true)) table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' Attack Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicAttackBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' Level Required') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicLevelRequired', true)) table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' % Damage Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicDamageBonus', true) .. '%') table.insert(resultPart, '\r\n!style="text-align:right;"| Two Handed?') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. (p._getItemStat(item, 'isTwoHanded') and 'Yes' or 'No')) table.insert(resultPart, '\r\n|}') return table.concat(resultPart) end function p.getArmourStatsBox(frame) local itemName = frame.args ~= nil and frame.args[1] or frame local item = p.getItem(itemName) if item == nil then return "ERROR: No item named "..itemName.." exists in the data module[[Category:Pages with script errors]]" end local ico = { ["Attack"] = Icons.Icon({'Attack', type='skill', notext=true}), ["Combat"] = Icons.Icon({'Combat', notext=true}), ["Defence"] = Icons.Icon({'Defence', type='skill', notext=true}), ["Magic"] = Icons.Icon({'Magic', type='skill', notext=true}), ["Ranged"] = Icons.Icon({'Ranged', type='skill', notext=true}), ["Strength"] = Icons.Icon({'Strength', type='skill', notext=true}), ["Slayer"] = Icons.Icon({'Slayer', type='skill', notext=true}) } local resultPart = {} table.insert(resultPart, '{| class="wikitable"\r\n|-\r\n!colspan="4" style="border-bottom:solid medium black;"| Armour Stats') table.insert(resultPart, '\r\n|-\r\n!colspan="2" style="border-bottom:solid thin black;"| Offensive Stats') table.insert(resultPart, '\r\n!colspan="2" style="border-bottom:solid thin black;"| Defensive Stats') table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Strength'] .. ' Strength Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'meleeStrengthBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Defence'] .. ' Defence Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'meleeDefenceBonus', true)) table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Stab Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'stabAttackBonus', 0)) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Defence'] .. ' Damage Reduction') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'damageReduction', true) .. '%') table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Slash Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'slashAttackBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Defence Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedDefenceBonus', true)) table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Combat'] .. ' Block Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'blockAttackBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;border-bottom:solid thin black;"| ' .. ico['Magic'] .. ' Defence Bonus') table.insert(resultPart, '\r\n|style="text-align:right;border-bottom:solid thin black;"| ' .. p._getItemStat(item, 'magicDefenceBonus', true)) table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Attack Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedAttackBonus', true)) table.insert(resultPart, '\r\n!colspan="2" style="border-bottom:solid thin black;"| Other') table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Strength Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedStrengthBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Slayer'] .. ' Bonus Slayer XP') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'slayerBonusXP', true) .. '%') table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' Attack Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicAttackBonus', true)) table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Defence'] .. ' Level Required') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'defenceLevelRequired', true)) table.insert(resultPart, '\r\n|-\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' % Damage Bonus') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicDamageBonus', true) .. '%') table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Ranged'] .. ' Level Required') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'rangedLevelRequired', true)) table.insert(resultPart, '\r\n|-\r\n| colspan="2"|') table.insert(resultPart, '\r\n!style="text-align:right;"| ' .. ico['Magic'] .. ' Level Required') table.insert(resultPart, '\r\n|style="text-align:right;"| ' .. p._getItemStat(item, 'magicLevelRequired', true)) table.insert(resultPart, '\r\n|}') return table.concat(resultPart) end return p