Module:Sandbox/LVL: Difference between revisionsGive feedback
Jump to navigation
Jump to search
No edit summary |
No edit summary |
||
| Line 10: | Line 10: | ||
local hero_data_module = require('Module:HeroData') | local hero_data_module = require('Module:HeroData') | ||
local function get_nested_stat_value(hero_data, stat_key | local function get_nested_stat_value(hero_data, stat_key) | ||
if hero_data[stat_key] ~= nil then | if hero_data[stat_key] ~= nil then | ||
return hero_data[stat_key] | return hero_data[stat_key] | ||
| Line 65: | Line 62: | ||
"ReloadSingle", | "ReloadSingle", | ||
"BulletSpeed", | "BulletSpeed", | ||
"FalloffStartRange", | "FalloffStartRange", | ||
"FalloffEndRange", | "FalloffEndRange", | ||
"CritDamageBonusPercent", | "CritDamageBonusPercent", | ||
"RoundsPerSecondAtMaxSpin", | "RoundsPerSecondAtMaxSpin", | ||
| Line 80: | Line 75: | ||
"TechResist", | "TechResist", | ||
"MeleeResist", | "MeleeResist", | ||
"CritDamageReceivedPercent", | |||
"DebuffResist", | |||
"BulletLifesteal", | "BulletLifesteal", | ||
"MaxMoveSpeed", | "MaxMoveSpeed", | ||
"SprintSpeed", | "SprintSpeed", | ||
"StaminaCooldown", | "StaminaCooldown", | ||
"Stamina", | "Stamina", | ||
"GroundDashSpeed" | "GroundDashSpeed", | ||
"GravityChange" | |||
}, | }, | ||
Spirit = { | Spirit = { | ||
| Line 107: | Line 104: | ||
end) | end) | ||
local function | -- Helper to generate a single row (primary or alt-fire) | ||
local function generateRow(hero_data, hero_key, is_alt_fire) | |||
local row_str = "" | |||
local row_str | local hero_name_local = localize(hero_key, hero_key) | ||
local | |||
local hero_name_en = hero_data["Name"] | local hero_name_en = hero_data["Name"] | ||
if | local template_args = {[1] = hero_name_en, l1 = hero_name_local} | ||
local hero_icon = mw.getCurrentFrame():expandTemplate{ title = "Template:HeroIcon", args = template_args } | |||
local hero_cell_content = hero_icon | |||
if is_alt_fire then | |||
hero_cell_content = hero_icon .. ' <small>(Alt-fire)</small>' | |||
end | end | ||
row_str = row_str .. | row_str = row_str .. | ||
'<td style="position: sticky; left: 0; z-index: 10; background-color: #202122; isolation: isolate; overflow: hidden;">' .. | '<td style="position: sticky; left: 0; z-index: 10; background-color: #202122; isolation: isolate; overflow: hidden;">' .. | ||
hero_cell_content .. "</td>" | |||
for _, category in ipairs(attribute_orders["category_order"]) do | for _, category in ipairs(attribute_orders["category_order"]) do | ||
if stats_to_include[category] ~= nil then | if stats_to_include[category] ~= nil then | ||
for _, attr_key in ipairs(stats_to_include[category]) do | for _, attr_key in ipairs(stats_to_include[category]) do | ||
-- Base value: alt-fire weapon stats from AltFire table, else normal lookup | |||
local base_value | |||
if is_alt_fire and category == "Weapon" then | |||
base_value = (hero_data.Weapon.AltFire and hero_data.Weapon.AltFire[attr_key]) or 0 | |||
else | |||
base_value = get_nested_stat_value(hero_data, attr_key) | |||
end | |||
local stat_value = base_value | |||
local stat_value | |||
if | -- FIX 1: Scale using AltFire key only if the stat actually exists in AltFire | ||
local scaling_data | |||
if is_alt_fire and hero_data.Weapon and hero_data.Weapon.AltFire and hero_data.Weapon.AltFire[attr_key] ~= nil then | |||
scaling_data = hero_data_module.get_hero_scaling_data(hero_data, attr_key .. "AltFire") | scaling_data = hero_data_module.get_hero_scaling_data(hero_data, attr_key .. "AltFire") | ||
else | |||
scaling_data = hero_data_module.get_hero_scaling_data(hero_data, attr_key) | scaling_data = hero_data_module.get_hero_scaling_data(hero_data, attr_key) | ||
end | end | ||
local scaling_strs = "" | |||
local spirit_scale = 0 | |||
local level_scale = 0 | |||
if scaling_data ~= nil then | if scaling_data ~= nil then | ||
| Line 189: | Line 184: | ||
) | ) | ||
local weapon_table = hero_data.Weapon | |||
if is_alt_fire and weapon_table and weapon_table.AltFire then | |||
weapon_table = weapon_table.AltFire | |||
end | |||
local hit_once = "false" | local hit_once = "false" | ||
if (attr_key == "DPS" or attr_key == "SustainedDPS") | if (attr_key == "DPS" or attr_key == "SustainedDPS") | ||
and weapon_table | |||
and weapon_table.HitOnceAcrossAllBullets | |||
then | |||
hit_once = "true" | |||
end | end | ||
| Line 222: | Line 216: | ||
end | end | ||
-- Build table body rows | -- Build table body rows (primary + optional alt-fire) | ||
for _, hero_entry in ipairs(sorted_heroes) do | for _, hero_entry in ipairs(sorted_heroes) do | ||
local hero_key = hero_entry.key | |||
local hero_data = hero_entry.data | |||
if | body_str = body_str .. generateRow(hero_data, hero_key, false) | ||
body_str = body_str .. | if hero_data.Weapon and hero_data.Weapon.AltFire then | ||
body_str = body_str .. generateRow(hero_data, hero_key, true) | |||
end | end | ||
end | end | ||
-- Pre-pass: determine which stats have any scaling, and which have both types | -- Pre-pass: determine which stats have any scaling, and which have both types | ||
-- (now includes alt-fire scaling for weapon columns) | |||
local stats_with_any_scaling = {} | local stats_with_any_scaling = {} | ||
local stats_with_both_scaling = {} | local stats_with_both_scaling = {} | ||
| Line 239: | Line 236: | ||
if stats_to_include[category] ~= nil then | if stats_to_include[category] ~= nil then | ||
for _, attr_key in ipairs(stats_to_include[category]) do | for _, attr_key in ipairs(stats_to_include[category]) do | ||
-- Primary scaling | |||
local scaling_data = hero_data_module.get_hero_scaling_data(hero_data, attr_key) | local scaling_data = hero_data_module.get_hero_scaling_data(hero_data, attr_key) | ||
if scaling_data ~= nil and next(scaling_data) ~= nil then | |||
if | |||
stats_with_any_scaling[attr_key] = true | stats_with_any_scaling[attr_key] = true | ||
local has_spirit = false | local has_spirit = false | ||
local has_level = false | local has_level = false | ||
for _, scaling_type in pairs(scaling_data) do | |||
if scaling_type == "Spirit" then has_spirit = true end | |||
if scaling_type == "Level" then has_level = true end | |||
end | end | ||
if has_spirit and has_level then | if has_spirit and has_level then | ||
stats_with_both_scaling[attr_key] = true | stats_with_both_scaling[attr_key] = true | ||
end | |||
end | |||
-- FIX 2: Alt-fire scaling only for stats that actually appear in AltFire | |||
if hero_data.Weapon | |||
and hero_data.Weapon.AltFire | |||
and hero_data.Weapon.AltFire[attr_key] ~= nil | |||
then | |||
local alt_scaling = hero_data_module.get_hero_scaling_data(hero_data, attr_key .. "AltFire") | |||
if alt_scaling ~= nil and next(alt_scaling) ~= nil then | |||
stats_with_any_scaling[attr_key] = true | |||
local has_spirit_alt = false | |||
local has_level_alt = false | |||
for _, scaling_type in pairs(alt_scaling) do | |||
if scaling_type == "Spirit" then has_spirit_alt = true end | |||
if scaling_type == "Level" then has_level_alt = true end | |||
end | |||
if has_spirit_alt and has_level_alt then | |||
stats_with_both_scaling[attr_key] = true | |||
end | |||
end | end | ||
end | end | ||