Module:Mod

-- -- Module for mod related templates --

local getArgs = require('Module:Arguments').getArgs local m_util = require('Module:Util') local m_cargo = require('Module:Cargo') local m_game = require('Module:Game') local f_item_link = require('Module:Item link').item_link

local p = {}

-- -- Strings -- -- This section contains strings used by this module. -- Add new strings here instead of in-code directly, this will help other -- people to correct spelling mistakes easier and help with translation to -- other PoE wikis.

local i18n = { categories = { mods = 'Mods', },   tooltips = { -- intro texts intro_named_id = "%s is the internal id of modifier %s.\n", intro_unnamed_id = "%s is the internal id of an unnamed modifier.\n", -- core data id = 'Mod Id', name = 'Name', mod_group = 'Group', mod_type = 'Mod type', domain = 'Domain', domain_fmt = '%s (Id: %s)', generation_type = 'Generation type', generation_type_fmt = '%s (Id: %s)', required_level = 'Req. Level', stat_text = 'Effect', granted_buff_id = 'Granted Buff Id', granted_buff_value = 'Granted Buff Value', granted_skill = 'Granted Skill', tags = 'Tags', tier_text = 'Tier Text', -- shared ordinal = '#', -- stats stats = 'Stats', stat_id = 'Stat Id', min = 'Minimum', max = 'Maximum', -- weights spawn_weights = 'Spawn weights', generation_weights = 'Generation weights', tag = 'Tag', weight = 'Weight', -- sell price sell_price = 'Modifier sell price', item = 'Item', },   errors = { --       -- Mod template --       sell_price_duplicate_name = 'Do not specify a sell price item name multiple times. Adjust the amount instead.', sell_price_missing_argument = 'Both %s and %s must be specified', },

}

-- -- utility / Helper functions --

local h = {}

-- -- Templates --

-- -- Template: Mod --

local mod_map = { main = { table = 'mods', display_order = {'id', 'name', 'mod_group', 'mod_type', 'domain', 'generation_type', 'required_level', 'stat_text', 'granted_buff_id', 'granted_buff_value', 'granted_skill', 'tags', 'tier_text'}, order = {'id', 'name', 'mod_group', 'mod_type', 'domain', 'generation_type', 'required_level', 'stat_text', 'stat_text_raw', 'granted_buff_id', 'granted_buff_value', 'granted_skill', 'tags', 'tier_text'}, fields = { id = { name = 'id', field = 'id', type = 'String', wikitext = i18n.tooltips.id, },           name = { name = 'name', field = 'name', type = 'String', wikitext = i18n.tooltips.name, },           mod_group = { name = 'mod_group', field = 'mod_group', type = 'String', wikitext = i18n.tooltips.mod_group, },           mod_type = { name = 'mod_type', field = 'mod_type', type = 'String', wikitext = i18n.tooltips.mod_type, },           domain = { name = 'domain', field = 'domain', type = 'Integer', wikitext = 'Mod domain', display = function (value) return string.format(i18n.tooltips.domain_fmt, m_game.constants.mod.domains[value]['short_upper'], value) end, },           generation_type = { name = 'generation_type', field = 'generation_type', type = 'Integer', wikitext = i18n.tooltips.generation_type, display = function (value) return string.format(i18n.tooltips.generation_type_fmt, m_game.constants.mod.generation_types[value]['short_upper'], value) end, },           required_level = { name = 'required_level', field = 'required_level', type = 'Integer', wikitext = i18n.tooltips.required_level, },           stat_text = { name = 'stat_text', field = 'stat_text', type = 'Text', wikitext = i18n.tooltips.stat_text, },           stat_text_raw = { name = nil, field = 'stat_text_raw', type = 'Text', func = function(tpl_args, frame) if tpl_args.stat_text then tpl_args.stat_text_raw = string.gsub(                           -- x -> x                            string.gsub( tpl_args.stat_text, '%[%[([^%]|]+)%]%]', '%1' ),                            -- x|y -> y                            '%[%[[^|]+|([^%]|]+)%]%]', '%1'                        )                    end                    return tpl_args.stat_text_raw                end            },            granted_buff_id = {                name = 'granted_buff_id',                field = 'granted_buff_id',                type = 'String',                wikitext = i18n.tooltips.granted_buff_id,            },            granted_buff_value = {                name = 'granted_buff_value',                field = 'granted_buff_value',                type = 'Integer',                wikitext = i18n.tooltips.granted_buff_value,            },            granted_skill = {                name = 'granted_skill',                field = 'granted_skill',                type = 'String',                wikitext = i18n.tooltips.granted_skill,            },            tags = {                name = 'tags',                field = 'tags',                type = 'List  of String',                wikitext = 'Tags',                 display = function(value)                    return table.concat(value, ', ')                  end,                default = {},            },            tier_text = {                name = 'tier_text',                field = 'tier_text',                type = 'Text',                wikitext = i18n.tooltips.tier_text,            },        },    },    mod_sell_prices = {        table = 'mod_sell_prices',        order = {'name', 'amount'},        fields = {            name = {                name = 'name',                field = 'name',                type = 'String',                func = function (value) return value end,            },            amount = {                name = 'amount',                field = 'amount',                type = 'Integer',                func = tonumber,            },        },    }, }

p.table_main = m_cargo.declare_factory{data=mod_map.main} p.table_mod_sell_prices = m_cargo.declare_factory{data=mod_map.mod_sell_prices}

function p.table_mod_stats(frame) m_cargo.declare(frame, {       _table = 'mod_stats',        id = 'String',        min = 'Integer',        max = 'Integer',    }) end

-- p.mod{id = "LocalIncreasedPhysicalDamagePercentUniqueOneHandSword2", name = "", mod_group = "LocalPhysicalDamagePercent", domain = "1", generation_type = "3", required_level = "1", mod_type = "LocalPhysicalDamagePercent", stat_text = "150% increased Physical Damage", stat1_id = "local_physical_damage_+%", stat1_min = "150", stat1_max = "150"} function p.mod(frame) -- Get args tpl_args = getArgs(frame, {       parentFirst = true    }) frame = m_util.misc.get_frame(frame) --   -- Validation & semantic properties --   -- Validate single value properties and set them m_util.args.from_cargo_map{ tpl_args=tpl_args, frame=frame, table_map=mod_map.main, }   -- Validate % set the stat subobjects m_util.args.stats(tpl_args, {frame=frame}) for _, stat_data in pairs(tpl_args.stats) do       m_cargo.store(frame, {            _table = 'mod_stats',             id = stat_data.id,            min = stat_data.min,            max = stat_data.max,        }) end -- Validate & set spawn weight subobjects m_util.args.spawn_weight_list(tpl_args, {       frame=frame,     }) -- Validate & set generation weight subobjects m_util.args.generation_weight_list(tpl_args, {       frame=frame,     }) -- Validate & set mod sell values i = 0 local names = {} local sell_prices = {} repeat i = i + 1 local id = {} value = {} for key, data in pairs(mod_map.mod_sell_prices.fields) do           id[key] = string.format('%s%s_%s', 'sell_price', i, data.name) value[key] = data.func(tpl_args[id[key]]) end if value.name == nil and value.amount == nil then value = nil elseif value.name ~= nil and value.amount ~= nil then if names[value.name] then error(i18n.errors.sell_price_duplicate_name) else names[value.name] = true end

local cargo_data = { _table = mod_map.mod_sell_prices.table, }           for key, data in pairs(mod_map.mod_sell_prices.fields) do                cargo_data[data.field] = value[key] end m_cargo.store(frame, cargo_data) sell_prices[#sell_prices+1] = value else error (string.format(i18n.errors.sell_price_missing_arguments, id.name, id.amount)) end until value == nil --   -- Display --   local container = mw.html.create('div') container :attr('class', 'modbox') -- core stats local tbl = container:tag('table') tbl :attr('class', 'wikitable') for _, key in ipairs(mod_map.main.display_order) do       local data = mod_map.main.fields[key] local text if data.display == nil then text = tpl_args[key] else text = data.display(tpl_args[key]) end tbl :tag('tr') :tag('th') :wikitext(data.wikitext) :done :tag('td') :wikitext(text) :done :done :done end -- stat table tbl = container:tag('table') tbl :attr('class', 'wikitable sortable') :tag('tr') :tag('th') :attr('colspan', 4) :wikitext(i18n.tooltips.stats) :done :done :tag('tr') :tag('th') :wikitext(i18n.tooltips.ordinal) :done :tag('th') :wikitext(i18n.tooltips.stat_id) :done :tag('th') :wikitext(i18n.tooltips.min) :done :tag('th') :wikitext(i18n.tooltips.max) :done :done :done for i=1, #tpl_args.stats do       local value = { id = tpl_args['stat' .. i .. '_id'], min = tpl_args['stat' .. i .. '_min'], max = tpl_args['stat' .. i .. '_max'], }       if value.id then tbl :tag('tr') :tag('td') :wikitext(i) :done :tag('td') :wikitext(value.id) :done :tag('td') :wikitext(value.min) :done :tag('td') :wikitext(value.max) :done :done :done end end -- spawn weight table tbl = container:tag('table') tbl :attr('class', 'wikitable sortable') :tag('tr') :tag('th') :attr('colspan', 3) :wikitext(i18n.tooltips.spawn_weights) :done :done :tag('tr') :tag('th') :wikitext(i18n.tooltips.ordinal) :done :tag('th') :wikitext(i18n.tooltips.tag) :done :tag('th') :wikitext(i18n.tooltips.weight) :done :done :done i = 0 value = nil repeat i = i + 1 value = { tag = tpl_args[string.format('spawn_weight%s_tag', i)], value = tpl_args[string.format('spawn_weight%s_value', i)], }       if value.tag then tbl :tag('tr') :tag('td') :wikitext(i) :done :tag('td') :wikitext(value.tag) :done :tag('td') :wikitext(value.value) :done :done :done end until value.tag == nil -- generation weight table tbl = container:tag('table') tbl :attr('class', 'wikitable sortable') :tag('tr') :tag('th') :attr('colspan', 3) :wikitext(i18n.tooltips.generation_weights) :done :done :tag('tr') :tag('th') :wikitext(i18n.tooltips.ordinal) :done :tag('th') :wikitext(i18n.tooltips.tag) :done :tag('th') :wikitext(i18n.tooltips.weight) :done :done :done i = 0 value = nil repeat i = i + 1 value = { tag = tpl_args[string.format('generation_weight%s_tag', i)], value = tpl_args[string.format('generation_weight%s_value', i)], }       if value.tag then tbl :tag('tr') :tag('td') :wikitext(i) :done :tag('td') :wikitext(value.tag) :done :tag('td') :wikitext(value.value) :done :done :done end until value.tag == nil -- Sell prices tbl = container:tag('table') tbl :attr('class', 'wikitable sortable') :tag('tr') :tag('th') :attr('colspan', 2) :wikitext(i18n.tooltips.sell_price) :done :done :tag('tr') :tag('th') :wikitext(i18n.tooltips.ordinal) :done :tag('th') :wikitext(i18n.tooltips.item) :done :done :done for i, value in ipairs(sell_prices) do       tbl :tag('tr') :tag('td') :wikitext(value.amount) :done :tag('td') :wikitext(string.format('%s', value.name)) :done :done end -- Generic messages on the page out = {} if mw.ustring.find(tpl_args['id'], '_') then out[#out+1] = frame:expandTemplate{ title = 'Incorrect title', args = { title=tpl_args['id'] } } .. '\n\n\n' end if tpl_args['name'] then out[#out+1] = string.format(i18n.tooltips.intro_named_id, tpl_args['id'], tpl_args['name']) else out[#out+1] = string.format(i18n.tooltips.intro_unnamed_id, tpl_args['id']) end -- Categories cats = {i18n.categories.mods} -- Done -> output return tostring(container) .. m_util.misc.add_category(cats) .. '\n' .. table.concat(out) end

return p