Jump to content

Welcome to King Warz Charts Wiki! Please note that the site is still under construction as I work on creating past chart week pages, as well as templates and pages for artists, songs, and albums. Because of this, you may see a lot of red links throughout the site.

Module:SongType

From King Warz Charts

Documentation for this module may be created at Module:SongType/doc

-- Module:SongType (fixed)
-- Infers (and optionally links) a song "Type" from |peak=.
-- Honors a manual override via |type= (or |override=).
-- Use |link=no when you need plain text.
local p = {}
local super_to_norm = {
    ["⁰"]="0", ["¹"]="1", ["²"]="2", ["³"]="3", ["⁴"]="4",
    ["⁵"]="5", ["⁶"]="6", ["⁷"]="7", ["⁸"]="8", ["⁹"]="9"
}
local function trim(s)
    return (tostring(s or ""):gsub("^%s+", ""):gsub("%s+$", ""))
end
local function superscripts_to_number(sup)
    local norm = {}
    for uchar in mw.ustring.gmatch(sup or "", ".") do
        local d = super_to_norm[uchar]
        if not d then return nil end
        table.insert(norm, d)
    end
    return tonumber(table.concat(norm))
end
local function unlink(text)
    text = trim(text or "")
    text = mw.ustring.gsub(text, "^%s*%[%[", "")
    text = mw.ustring.gsub(text, "%]%]%s*$", "")
    local pipe = mw.ustring.find(text, "|", 1, true)
    if pipe then text = mw.ustring.sub(text, 1, pipe - 1) end
    return trim(text)
end
local function linkify(label, want_link)
    label = trim(label or "")
    if label == "" then return "" end
    if want_link == false then return label end
    return string.format("[[%s]]", label)
end
local function infer_from_peak(peak_raw, want_link)
    local peak = trim(peak_raw)
    if peak == "" then return nil end

    -- Extract leading numeric part
    local position_str, rest = peak:match("^(%d+)(.*)$")
    if not position_str then return nil end
    local position = tonumber(position_str)

    if position == 1 then
        if rest == "" then
            return linkify("No.1 Hit Song", want_link)
        end
        local super_only = true
        for uchar in mw.ustring.gmatch(rest, ".") do
            if not super_to_norm[uchar] then super_only = false; break end
        end
        if super_only then
            local expn = superscripts_to_number(rest)
            if expn then
                return (expn >= 5) and linkify("Major Hit Song", want_link)
                                   or  linkify("No.1 Hit Song", want_link)
            end
        end
        local caret_num = peak:match("^1%^%s*(%d+)$")
        if caret_num then
            local expn = tonumber(caret_num)
            if expn then
                return (expn >= 5) and linkify("Major Hit Song", want_link)
                                   or  linkify("No.1 Hit Song", want_link)
            end
        end
    elseif position >= 2 and position <= 60 then
        -- For non-1, ignore rest (superscripts), use position
        if position <= 5 then
            return linkify("Top 5 Hit Song", want_link)
        elseif position <= 10 then
            return linkify("Top 10 Hit Song", want_link)
        elseif position <= 20 then
            return linkify("Top 20 Hit Song", want_link)
        else
            return linkify("Charted Song", want_link)
        end
    end
    return nil
end
function p.inferType(frame)
    -- IMPORTANT: prefer module-call args first, then fall back to parent
    local margs = frame.args or {}
    local pargs = (frame:getParent() and frame:getParent().args) or {}
    local peak  = margs.peak or pargs.peak or margs["peak"] or pargs["peak"] or ""
    local link  = margs.link or pargs.link
    local want  = not (link == "no" or link == "false" or link == "0")
    -- Manual override (|type= or |override=), from either scope
    local override = margs.override or pargs.override or margs.type or pargs.type
    override = trim(override or "")
    if override ~= "" then
        local clean = unlink(override)
        return linkify(clean, want)
    end
    local t = infer_from_peak(peak, want)
    return t or ""
end
return p