Module:SpawningMap

From Primal Fear Wiki
Jump to navigation Jump to search

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

local p = {}

local Arguments = require( 'Dev:Arguments' )
local Variables = mw.ext.VariablesLua

local MAP_SIZE = 290
local MAPS = {
    { 'The Island', 'The Island Topographic Map.jpg' },
    { 'The Center', 'The Center Topographic Map.jpg' },
    { 'Scorched Earth', 'Scorched Earth Topographic Map.jpg' },
    { 'Ragnarok', 'Ragnarok Ocean Topographic Map.jpg' },
    { 'Aberration', 'Aberration Topographic Map.jpg' },
    { 'Extinction', 'Extinction Topographic Map.jpg' },
    { 'Valguero', 'Valguero Topographic Map.jpg' },
    { 'Genesis: Part 1', 'Genesis Part 1 Topographic Map.jpg' },
    { 'Crystal Isles', 'Crystal Isles Topographic Map.jpg' },
    { 'Genesis: Part 2', 'Genesis Part 2 Map.jpg' },
    { 'Lost Island', 'Lost Island map.jpg' },
    { 'Fjordur Midgard', 'Fjordur Map.jpg', tabOf = 'Fjordur', tabName = 'Midgard' },
    { 'Fjordur Asgard', 'Fjordur Asgard Topographic Map.jpg', tabOf = 'Fjordur', tabName = 'Asgard' },
    { 'Fjordur Jotunheim', 'Fjordur Jotunheim Topographic Map.jpg', tabOf = 'Fjordur', tabName = 'Jotunheim' },
    { 'Fjordur Vanaheim', 'Fjordur Vanaheim Topographic Map.jpg', tabOf = 'Fjordur', tabName = 'Vanaheim' }
}
local FILE_NAME_FORMAT = 'Spawning %s %s.svg'
local FILE_NAME_FORMAT_MOD = 'Mod %s Spawning %s %s.svg'

local IS_ENGLISH_WIKI = mw.getContentLanguage():getCode() == 'en'


local function getFileNameForMap( species, mod, map )
	map = map:gsub( ': ', ' ' )
    if mod ~= nil then
        return FILE_NAME_FORMAT_MOD:format( mod, species, map )
    end
    return FILE_NAME_FORMAT:format( species, map )
end


local function doesFileExist( name )
    return mw.title.new( ( IS_ENGLISH_WIKI and 'File:' or 'Media:' ) .. name ).file.exists
end


-- Iterates over statically configured maps and yields if overlays exist
local function findMapsForSpecies( species, mod )
    local results = {}

    for _, map in ipairs( MAPS ) do
        local fileName = getFileNameForMap( species, mod, map[1] )
        if doesFileExist( fileName ) then
            table.insert( results, { 
                displayName = map[1],
                background = map[2],
                overlay = fileName,
                tabOf = map.tabOf,
                tabName = map.tabName
            } )
        end
    end

    return results
end


-- Builds HTML node tree with map background and an overlay
local function displayMap( species, mod, map, size )
    return mw.html.create 'div'
        :attr( 'class', 'noviewer spawningMap-container' )
        :attr( 'style', string.format( 'position:relative;width:%dpx;height:%dpx', size, size ) )

        :tag 'div'
            :attr( 'class', 'spawningMap-map colorBlindToggleable' )
            :attr( 'style', 'position:absolute' )
            :wikitext( string.format('[[File:%s|link=|%dpx]]', map.background, size ) )
            :done()
        
        :tag 'div'
            :attr( 'class', 'svgCreatureMap colorBlindToggleable' )
            :attr( 'style', 'position:absolute' )
            :wikitext( string.format( '[[File:%s|link=|%dpx]]', map.overlay, size ) )
            :done()
end


function p.main( f )
	local args = Arguments.getArgs( f, {
		trim = true,
		removeBlanks = true,
	} )

    assert( args.species ~= nil, 'parameter "species" must be specified' )

    local queriedMaps = findMapsForSpecies( args.species, args.mod )
    if #queriedMaps <= 0 then
        return ''
    end

    local size = args.size or MAP_SIZE

    local tabs = {}
    local subTabs = {}
    -- Generate map tabs
    for _, map in ipairs( queriedMaps ) do
        local mapStack = displayMap( args.species, args.mod, map, size )
        local tabOutput = string.format( '%s=%s', map.tabName or map.displayName, tostring( mapStack ) )
        -- Append onto intermediate lists
        if map.tabOf then
            -- Sub-tabber. Create an intermediate list if tabber has not been initialised yet
            if subTabs[map.tabOf] == nil then
                subTabs[map.tabOf] = {}
                -- Insert a placeholder into the primary list
                table.insert( tabs, { map.tabOf } )
            end
            -- Append tab
            table.insert( subTabs[map.tabOf], tabOutput )
        else
            -- Append tab
            table.insert( tabs, tabOutput )
        end

        -- Expose to wikitext that the creature spawns on the map
        if args.defineSpawnsOnVariables == 'yes' then
            Variables.vardefine( string.format( 'SpawnsOn_%s', map.displayName:gsub( ' ', '' ):gsub( ':', '' ) ), '1' )
        end
    end

    -- Convert tabber placeholders into actual tabbers
    for index, data in ipairs( tabs ) do
        if type( data ) == 'table' then
            tabs[index] = string.format( '%s=%s', data[1], f:extensionTag {
                name = 'tabber',
                content = table.concat( subTabs[data[1]], '\n|-|' ) 
            } )
        end
    end

    return string.format( '<div class="spawningMap" style="width:%dpx">%s</div>%s',
    size + 10,
        f:extensionTag {
            name = 'tabber',
            content = table.concat( tabs, '\n|-|' )
        },
        ( args.nolegend ~= 'true' and args.nolegend ~= 'yes' ) and ( f:expandTemplate { title = 'RarityLegend', args = { size .. 'px' } } ) or ''
    )
end


return p