Editing Module:Abilities/cardGive feedback
Jump to navigation
Jump to search
The edit can be undone.
Please check the comparison below to verify that this is what you want to do, and then publish the changes below to finish undoing the edit.
| Latest revision | Your text | ||
| Line 2: | Line 2: | ||
local commonutils = require "Module:Utilities" | local commonutils = require "Module:Utilities" | ||
local utils = require "Module:Abilities/utils" | local utils = require "Module:Abilities/utils" | ||
local p = {} | local p = {} | ||
local data = mw.loadJsonData("Data:AbilityCards.json") | local data = mw.loadJsonData("Data:AbilityCards.json") | ||
-- Maps attr type to an appropriate image and page link | |||
-- Optional icon size, will be defaulted on the template | |||
local ATTR_TYPE_ICON_MAP = require("Module:Icon/attr") | |||
-- TODO - replace this with utils file | |||
function utils.get_ability_card_data(hero_key, ability_num) | |||
if(hero_key == nil) then return nil end | |||
return data[hero_key][tonumber(ability_num)] | |||
end | |||
| Line 15: | Line 24: | ||
if string.sub(hero_name, 1, 5) == "hero_" then return hero_name end | if string.sub(hero_name, 1, 5) == "hero_" then return hero_name end | ||
for i, hero in pairs(data) do | |||
return | if hero["Name"] == hero_name then | ||
return i | |||
end | |||
end | |||
return nil | |||
end | end | ||
| Line 63: | Line 76: | ||
local info1_desc = get_info_desc(hero_key, ability_num, 1) | local info1_desc = get_info_desc(hero_key, ability_num, 1) | ||
local info1_main_boxes = get_main_boxes(hero_key, ability_num, 1) | local info1_main_boxes = get_main_boxes(hero_key, ability_num, 1) | ||
-- Inject Hex Duration only for Rabbit Hex | |||
if ability.Key == "ability_magician_animalhexarea" | |||
and ability.Other | |||
and ability.Other.HexDuration | |||
and ability.Other.HexDuration.Value then | |||
local icon = get_icon("duration") | |||
table.insert(info1_main_boxes, 1, | |||
frame:expandTemplate{ | |||
title = "Ability_card_v2/Card/MainBox", | |||
args = { | |||
key = "HexDuration", | |||
value = ability.Other.HexDuration.Value, | |||
icon = icon.img, | |||
icon_link = icon.link, | |||
icon_color = icon.color, | |||
} | |||
}) | |||
end | |||
local info1_alt_boxes = get_alt_boxes(hero_key, ability_num, 1) | local info1_alt_boxes = get_alt_boxes(hero_key, ability_num, 1) | ||
| Line 101: | Line 133: | ||
channel_time = ability.AbilityChannelTime and ability.AbilityChannelTime.Value ~= 9999 and ability.AbilityChannelTime.Value, | channel_time = ability.AbilityChannelTime and ability.AbilityChannelTime.Value ~= 9999 and ability.AbilityChannelTime.Value, | ||
channel_time_ss = get_attr_ss(ability.AbilityChannelTime), | |||
radius = ability.Radius and ability.Radius.Value, | radius = ability.Radius and ability.Radius.Value, | ||
radius_ss = get_attr_ss(ability.Radius), | |||
range = ability.AbilityCastRange and ability.AbilityCastRange.Value, | range = ability.AbilityCastRange and ability.AbilityCastRange.Value, | ||
range_ss = get_attr_ss(ability.AbilityCastRange), | |||
duration = ability.AbilityDuration and ability.AbilityDuration.Value, | duration = ability.AbilityDuration and ability.AbilityDuration.Value, | ||
duration_ss = get_attr_ss(ability.AbilityDuration), | |||
-- ability_width = format_value_with_prepost(width_key, ability[width_key]), | -- ability_width = format_value_with_prepost(width_key, ability[width_key]), | ||
cooldown =ability.AbilityCooldown and ability.AbilityCooldown.Value, | cooldown =ability.AbilityCooldown and ability.AbilityCooldown.Value, | ||
cooldown_ss = get_attr_ss(ability.AbilityCooldown), | |||
charge_cooldown = ability.AbilityCooldownBetweenCharge and ability.AbilityCooldownBetweenCharge.Value ~= -1 and ability.AbilityCooldownBetweenCharge.Value, | charge_cooldown = ability.AbilityCooldownBetweenCharge and ability.AbilityCooldownBetweenCharge.Value ~= -1 and ability.AbilityCooldownBetweenCharge.Value, | ||
charge_cooldown_ss = get_attr_ss(ability.AbilityCooldownBetweenCharge), | |||
num_of_charges = ability.AbilityCharges and ability.AbilityCharges.Value, | |||
num_of_charges = ability.AbilityCharges and ability.AbilityCharges.Value | |||
-- Info section #1 defined in "Info1" attribute | -- Info section #1 defined in "Info1" attribute | ||
| Line 195: | Line 215: | ||
end | end | ||
-- | -- Get spirit scaling of attribute, return nil if none is found | ||
function get_attr_ss(attr) | |||
if not attr then | |||
return nil | |||
if not attr then | |||
return nil | |||
end | end | ||
local scale = attr.Scale | local scale = attr.Scale | ||
if not scale then | if not scale then | ||
return nil | return nil | ||
end | end | ||
if scale. | if scale.Type ~= 'spirit' then | ||
return nil | return nil | ||
end | end | ||
| Line 255: | Line 234: | ||
end | end | ||
return | return commonutils.round_to_sig_fig(scale.Value, 3) | ||
end | end | ||
| Line 334: | Line 303: | ||
for k, prop in ipairs(props) do -- use ipairs for ordered iteration | for k, prop in ipairs(props) do -- use ipairs for ordered iteration | ||
local value = prop.Value | local value = prop.Value | ||
-- If it scales with melee damage, set the value using the hero's base melee to match in game visuals | -- If it scales with melee damage, set the value using the hero's base melee to match in game visuals | ||
if | if prop.Scale and prop.Scale.Type == 'melee' then | ||
local hero = get_hero_data(hero_key) | local hero = get_hero_data(hero_key) | ||
value = hero. | value = prop.Value + hero.LightMeleeDamage * prop.Scale.Value | ||
end | end | ||
local icon = | local icon = get_icon(prop.Type) | ||
local main_box | local main_box | ||
| Line 358: | Line 320: | ||
value = value, | value = value, | ||
status_effect = prop.StatusEffect, | status_effect = prop.StatusEffect, | ||
icon = | icon = icon.img, | ||
icon_link = | icon_link = icon.link, | ||
icon_color = | icon_color = icon.color, | ||
icon_size = | icon_size = icon.size, | ||
scale_value = | scale_value = prop.Scale and commonutils.round_to_sig_fig(prop.Scale.Value, 3), | ||
scale_type = | scale_type = prop.Scale and prop.Scale.Type, | ||
-- allow nil value here as some status effects don't have a value but should not be hidden | -- allow nil value here as some status effects don't have a value but should not be hidden | ||
hide = value == 0 and "true" or "false", | hide = value == 0 and "true" or "false", | ||
| Line 375: | Line 337: | ||
key = prop.Key, | key = prop.Key, | ||
value = value, | value = value, | ||
icon = | icon = icon.img, | ||
icon_link = | icon_link = icon.link, | ||
icon_color = | icon_color = icon.color, | ||
icon_size = | icon_size = icon.size, | ||
scale_value = | scale_value = prop.Scale and commonutils.round_to_sig_fig(prop.Scale.Value, 3), | ||
scale_type = | scale_type = prop.Scale and prop.Scale.Type, | ||
hide = (value == nil or value == 0) and "true" or "false", | hide = (value == nil or value == 0) and "true" or "false", | ||
} | } | ||
| Line 416: | Line 378: | ||
local alt_boxes = {} | local alt_boxes = {} | ||
for k, prop in pairs(props) do | |||
-- Some props don't have values, as those come from upgrades | |||
-- For now, we will ignore these and only show data for the base ability | |||
if prop.Value then | |||
local icon = get_icon(prop.Type) | |||
local alt_box = frame:expandTemplate{ | |||
title = "Ability_card_v2/Card/AltBox", | |||
args = { | |||
key = prop.Key, | |||
value = prop.Value, | |||
icon = icon.img, | |||
icon_link = icon.link, | |||
icon_color = icon.color, | |||
icon_size = icon.size, | |||
scale_value = prop.Scale and commonutils.round_to_sig_fig(prop.Scale.Value, 3), | |||
scale_type = prop.Scale and prop.Scale.Type, | |||
hide = prop.Value == 0 and "true" or "false", | |||
} | |||
} | |||
table.insert(alt_boxes, alt_box) | |||
end | |||
end | |||
return alt_boxes | return alt_boxes | ||
| Line 452: | Line 405: | ||
local UPGRADE_COST_MAP = {1, 2, 5} | local UPGRADE_COST_MAP = {1, 2, 5} | ||
function get_upgrade_boxes(hero_key, ability_num) | function get_upgrade_boxes(hero_key, ability_num) | ||
local ability = utils.get_ability_card_data(hero_key, ability_num) | local ability = utils.get_ability_card_data(hero_key, ability_num) | ||
| Line 471: | Line 414: | ||
local upgrade_boxes = {} | local upgrade_boxes = {} | ||
for k, upgrade in | for k, upgrade in pairs(upgrades) do | ||
local description = lang.get_string(upgrade.DescKey) | local description = lang.get_string(upgrade.DescKey) | ||
| Line 492: | Line 435: | ||
end | end | ||
-- | -- Vary the font size based on the number of characters to prevent overflow | ||
local fontsize = '1rem' | |||
local | if #description > 60 and #description < 71 then | ||
fontsize = '0.95rem' | |||
elseif #description > 70 and #description < 91 then | |||
fontsize = '0.875rem' | |||
elseif #description > 90 then | |||
fontsize = '0.8rem' | |||
end | |||
local upgrade_box = frame:expandTemplate{ | local upgrade_box = frame:expandTemplate{ | ||
title = "Ability_card_v2/Card/UpgradeBox", | title = "Ability_card_v2/Card/UpgradeBox", | ||
| Line 508: | Line 450: | ||
index = k, | index = k, | ||
cost = UPGRADE_COST_MAP[k], | cost = UPGRADE_COST_MAP[k], | ||
description = | description = frame:preprocess(description), | ||
scale_value = | scale_value = upgrade.Scale and commonutils.round_to_sig_fig(upgrade.Scale.Value, 3), | ||
scale_type = | scale_type = upgrade.Scale and upgrade.Scale.Type, | ||
fontsize = fontsize | |||
fontsize = | |||
} | } | ||
} | } | ||
| Line 525: | Line 464: | ||
function create_description(prop, frame) | function create_description(prop, frame) | ||
local | local description = '' | ||
local | local first = true | ||
local seen = {} | local seen = {} -- Set to track added combinations | ||
for k, v in pairs(prop) do | for k, v in pairs(prop) do | ||
if | local value | ||
if type(v) == 'table' then | |||
value = v.Value | |||
else | |||
value = v | |||
end | |||
local formatted_value = utils.format_value_with_prepost(k, value, frame) | |||
local attr_name = lang.get_string(k..'_label') | |||
local key = formatted_value .. '|' .. attr_name -- Unique identifier | |||
-- skip DescKey for the edge case where we are generating description instead of using localization files | |||
if k ~= 'DescKey' then | |||
-- Skip if this combination has already been added | |||
if not seen[key] then | |||
-- Add line break if this is not the first item | |||
if not first then | |||
description = description .. '<br>' | |||
end | |||
end | |||
description = description .. string.format('%s %s', formatted_value, attr_name) | |||
first = false | |||
seen[key] = true -- Mark this combination as added | |||
end | end | ||
end | end | ||
return description | |||
end | |||
p.get_attr_icon = function(frame) | |||
local attr_type = frame.args[1] | |||
local icon = get_icon(attr_type) | |||
return string.format('[[File:%s|%s|18px|link=%s]]', icon.img or '', icon.size or '', icon.link or '') | |||
end | |||
function get_icon(attr_type) | |||
local mappedAttr = ATTR_TYPE_ICON_MAP[attr_type] | |||
local img = 'GenericProperty.png' | |||
local link = '' | |||
local size = '' | |||
local color = 'Grey' | |||
if mappedAttr then | |||
img = mappedAttr.img | |||
link = mappedAttr.link | |||
size = mappedAttr.size | |||
color = mappedAttr.color or color | |||
end | |||
return {img=img, link=link, color=color, size=size} | |||
end | end | ||
| Line 668: | Line 604: | ||
icon = lang.get_string(ability.Key, 'en') .. '.png', | icon = lang.get_string(ability.Key, 'en') .. '.png', | ||
description = mw.getCurrentFrame():preprocess(lang.get_string(ability.DescKey)), | description = mw.getCurrentFrame():preprocess(lang.get_string(ability.DescKey)), | ||
radius = ability.Radius and ability.Radius.Value, | radius = ability.Radius and ability.Radius.Value, | ||
radius_ss = get_attr_ss(ability.Radius), | |||
range = ability.AbilityCastRange and ability.AbilityCastRange.Value, | range = ability.AbilityCastRange and ability.AbilityCastRange.Value, | ||
range_ss = get_attr_ss(ability.AbilityCastRange), | |||
duration = ability.AbilityDuration and ability.AbilityDuration.Value, | duration = ability.AbilityDuration and ability.AbilityDuration.Value, | ||
duration_ss = get_attr_ss(ability.AbilityDuration), | |||
-- ability_width = format_value_with_prepost(width_key, ability[width_key]), | -- ability_width = format_value_with_prepost(width_key, ability[width_key]), | ||
cooldown =ability.AbilityCooldown and ability.AbilityCooldown.Value, | cooldown =ability.AbilityCooldown and ability.AbilityCooldown.Value, | ||
cooldown_ss = get_attr_ss(ability.AbilityCooldown), | |||
charge_cooldown = ability.AbilityCooldownBetweenCharge and ability.AbilityCooldownBetweenCharge.Value, | |||
charge_cooldown_ss = get_attr_ss(ability.AbilityCooldownBetweenCharge), | |||
charge_cooldown = ability.AbilityCooldownBetweenCharge | num_of_charges = ability.AbilityCharges and ability.AbilityCharges.Value, | ||
notes = notes, | |||
notes_source_page = notes_source_page, | |||
} | } | ||
} | } | ||