Home
Random
Log in
Settings
About the Deadlock Wiki
Search
Editing
Module
:
StreetBrawlAbilities
Give feedback
Warning:
You are not logged in. Once you make an edit, a temporary account will be created for you.
Learn more
.
Log in
or
create an account
to continue receiving notifications after this account expires, and to access other features.
Anti-spam check. Do
not
fill this in!
-- Lists the Street Brawl ability overrides from [[Data:StreetBrawlData.json]] with the -- {{DataProp}} call that cites each one and the base value it replaces. local p = {} local SB_PAGE = "Data:StreetBrawlData.json" local CARDS_PAGE = "Data:AbilityCards.json" local HERO_PAGE = "Data:HeroData.json" local UNMATCHED = "Unmatched abilities" -- Maps each ability key to the hero who owns it. local function build_owner_map() local cards = mw.loadJsonData(CARDS_PAGE) local heroes = mw.loadJsonData(HERO_PAGE) local map = {} for hero_key, card in pairs(cards) do local hero = heroes[hero_key] -- Unreleased hero stubs reuse released heroes' ability keys (hero_gunslinger -- carries Paradox's Pulse Grenade), so only live hero records may claim one. if type(card) == "table" and hero and hero.Name and hero.IsDisabled ~= true then for slot = 1, 8 do -- The card's slot keys decode as numbers, so index with one. local ability = card[slot] or card[tostring(slot)] if type(ability) == "table" and ability.Key then map[ability.Key] = { hero = hero.Name, slot = slot, name = ability.Name } end end end end return map end -- Orders one node's keys: plain props before Upgrades, Value before Scale, tiers numerically. local function sorted_keys(node, top) local keys = {} for k in pairs(node) do -- Name labels the record; it is not one of the changed properties. if not (top and k == "Name") then keys[#keys + 1] = k end end table.sort(keys, function(a, b) if top then if a == "Upgrades" then return false end if b == "Upgrades" then return true end end if a == "Value" then return true end if b == "Value" then return false end local na, nb = tonumber(a), tonumber(b) if na and nb then return na < nb end -- Upgrade tiers arrive as numbers, so never compare a number with a string. return tostring(a) < tostring(b) end) return keys end -- Collects the changed properties as dot-notation paths, the form {{DataProp}} accepts. local function flatten(node, prefix, out, top) for _, key in ipairs(sorted_keys(node, top)) do local value = node[key] local path = prefix and (prefix .. "." .. key) or tostring(key) if type(value) == "table" then flatten(value, path, out, false) else out[#out + 1] = path end end end -- Reads a property both ways, returning its Street Brawl value and its normal one. local function both_values(frame, ability, prop) local sb = frame:expandTemplate{ title = "DataProp", args = { ability, prop, "streetbrawl" } } local base = frame:expandTemplate{ title = "DataProp", args = { ability, prop } } return tonumber(sb), tonumber(base) end -- Builds one property line: the wikitext to copy, its Street Brawl value, and the default. local function render_line(frame, ability, path) local call = "{{DataProp|" .. ability .. "|" .. path .. "|streetbrawl}}" -- Expanded rather than read from the JSON, so this shows what a copied call really gives. local sb = frame:expandTemplate{ title = "DataProp", args = { ability, path, "streetbrawl" } } local base = frame:expandTemplate{ title = "DataProp", args = { ability, path } } return "* <code>" .. mw.text.nowiki(call) .. "</code> → '''" .. sb .. "''' ''(default " .. base .. ")''" end -- True when Street Brawl changes at least one of this hero's abilities. Accepts a -- hero_* key or the hero's English name, so callers may pass whichever they hold. function p.hero_has_changes(hero) if hero == nil or hero == "" then return false end local record = mw.loadJsonData(HERO_PAGE)[hero] local name = (record and record.Name) or hero local owners = build_owner_map() local changes = mw.loadJsonData(SB_PAGE)["ability-changes"] for key in pairs(changes) do local owner = owners[key] if owner and owner.hero == name then return true end end return false end -- {{#invoke:StreetBrawlAbilities|hasChanges|HERO}} exposes the same check to wikitext, -- answering "1" or the empty string so #if can branch on it. function p.hasChanges(frame) return p.hero_has_changes(mw.text.trim(frame.args[1] or "")) and "1" or "" end -- {{#invoke:StreetBrawlAbilities|change|ABILITY|PROP}} describes how far a property moved -- in Street Brawl, as "reduced by 45%" or "increased by ~40%". function p.change(frame) local ability = mw.text.trim(frame.args[1] or "") local prop = mw.text.trim(frame.args[2] or "") local sb, base = both_values(frame, ability, prop) -- DataProp answers a failed lookup with a red notice rather than a number. if not sb or not base or base == 0 then return '<span style="color:red;">No change for ' .. ability .. '/' .. prop .. '</span>' end -- Properties Street Brawl leaves alone fall back to the base value, so two equal -- numbers mean this property was never in the overlay. if sb == base then return '<span style="color:red;">Street Brawl does not change ' .. ability .. '/' .. prop .. '</span>' end -- Purely a comparison of the two numbers; whether that helps or hurts the hero is -- for the surrounding prose to say. local direction = sb > base and "increased" or "reduced" local percent = math.abs(sb - base) / math.abs(base) * 100 -- Rounded to the nearest 5% so the prose reads as a round figure; when that rounding -- moves the number by more than 1.5 points, "~" marks it as approximate. local rounded = math.floor(percent / 5 + 0.5) * 5 local approx = math.abs(percent - rounded) > 1.5 and "~" or "" return direction .. " by " .. approx .. string.format("%.0f", rounded) .. "%" end -- {{#invoke:StreetBrawlAbilities|report}} renders every change, grouped by hero. function p.report(frame) local changes = mw.loadJsonData(SB_PAGE)["ability-changes"] local owners = build_owner_map() local by_hero, hero_order = {}, {} for key, record in pairs(changes) do local owner = owners[key] local hero = owner and owner.hero or UNMATCHED if not by_hero[hero] then by_hero[hero] = {} hero_order[#hero_order + 1] = hero end local paths = {} flatten(record, nil, paths, true) table.insert(by_hero[hero], { slot = owner and owner.slot or 99, name = record.Name or (owner and owner.name) or key, paths = paths, }) end -- Anything the data adds that no live hero claims is listed last rather than dropped. table.sort(hero_order, function(a, b) if a == UNMATCHED then return false end if b == UNMATCHED then return true end return a < b end) local out = {} for _, hero in ipairs(hero_order) do local abilities = by_hero[hero] table.sort(abilities, function(a, b) return a.slot < b.slot end) local matched = hero ~= UNMATCHED out[#out + 1] = "\n== " .. (matched and frame:expandTemplate{ title = "HeroIcon", args = { hero } } or hero) .. " ==" for _, ability in ipairs(abilities) do out[#out + 1] = "=== " .. (matched and frame:expandTemplate{ title = "AbilityIcon", args = { ability.name } } or ability.name) .. " ===" for _, path in ipairs(ability.paths) do out[#out + 1] = render_line(frame, ability.name, path) end end end return table.concat(out, "\n") end return p
Summary:
Please note that all contributions to The Deadlock Wiki are considered to be released under the Creative Commons Attribution-NonCommercial-ShareAlike (see
Deadlock:Copyrights
for details). If you do not want your writing to be edited mercilessly and redistributed at will, then do not submit it here.
You are also promising us that you wrote this yourself, or copied it from a public domain or similar free resource.
Do not submit copyrighted work without permission!
Cancel
Editing help
(opens in new window)
Preview page with this template
Page included on this page:
Module:StreetBrawlAbilities/doc
(
view source
)