Module:Weapon stats

From Mobius Final Fantasy Wiki
Jump to: navigation, search

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

local mArguments -- lazy load.

local p = {}

local title = mw.title.getCurrentTitle()
local PAGENAME = title.text
local NAMESPACE = title.namespace
local MAX = {
	["HP"] = 2000,
	["Attack"] = 200,
	["Break Power"] = 200,
	["Magic"] = 200,
	["Crit Chance"] = 5,
	["Speed"] = 2,
	["Defense"] = 5,
}
local BLACK = mw.ustring.char(0x2605) -- "★"
local WHITE = mw.ustring.char(0x2606) -- "★"

local function parse_attrs(name, values)
	local name = name or ""
	local values = values or ""
	local max = MAX[name]
	local t = {nil, nil, nil, nil, nil}
	for i,x in ipairs(mw.text.split(values, "%s*,%s*")) do
		t[i] = tonumber(mw.text.trim(x))
	end
	t.name = name
	t[5] = max
	return t
end

local function parse_stars(name, values)
	local name = name or ""
	local values = values or ""
	local max = MAX[name]
	local t = {nil, nil, nil, nil, nil}
	for i,x in ipairs(mw.text.split(values, "%s*,%s*")) do
		x = mw.text.trim(x)
		local black, count = x:gsub(BLACK, "*"):match("^([%*]*)x?(%d*)")
		if count ~= "" and (black == "" or black == "*") then
			t[i] = tonumber(count)
		elseif black ~= "" then
			t[i] = #black
		end
	end
	t.name = name
	t[5] = max
	return t
end
	
local function parse_ability(name, values, mod, max)
	local name = name or "???"
	local values = values or ""
	local mod = tonumber(string.match(mod or '', '^%s*([%+%-]?%d*)%%?%s*$'))
	local max = tonumber(string.match(max or '', '^%s*([%+%-]?%d*)%%?%s*$'))
	local t = {nil, nil, nil, nil, nil}
	for i,x in ipairs(mw.text.split(values, "%s*,%s*")) do
		t[i] = tonumber(x:match("^%s*([%+%-]?%d*)%%?%s*$"))
	end
	t.name = name
	t.mod = mod
	t[5] = max
	return t
end
	
function p._main(args)
	if args == nil then return "" end
	local name = args.name or PAGENAME
	if (name == nil or name == "") then name = "???" end
	local caption = "Stats & Auto-Abilities of <em>"..name.."</em>"
	
	local data = {
		{BLACK..1, BLACK..2, BLACK..3, BLACK..4, BLACK..5, name="", mod="Mod", type="header"},
		-- Extract base attributes (HP, Attack, Break Power, Magic)
		parse_attrs("HP", args.hp),
		parse_attrs("Attack", args.atk),
		parse_attrs("Break Power", args.brk),
		parse_attrs("Magic", args.mag),
		-- Extract stars (Crit Chance, Speed, and Defense)
		parse_stars("Crit Chance", args.crt or args.cri),
		parse_stars("Speed", args.spd),
		parse_stars("Defense", args.def),
		-- Extract auto-abilities (1, 2, 3, 4)
		parse_ability(args.abi1, args.val1, args.mod1, args.max1),
		parse_ability(args.abi2, args.val2, args.mod2, args.max2),
		parse_ability(args.abi3, args.val3, args.mod3, args.max3),
		parse_ability(args.abi4, args.val4, args.mod4, args.max4),
		-- @todo Find weapon that hasn't got hidden "Boost Ultimate+1" as 4th.
		parse_ability("Boost Ultimate", nil, "1", "1"),
	}
	
	-- Storage
	if NAMESPACE == 0 then
		local frame = mw.getCurrentFrame()
		for i=1,4 do
			local cargoData = {
				_table = 'weapon_stats',
				rarity = i,
			}
			for _,stat in ipairs(data) do
				local key = stat.name:lower():gsub(" ", "_")
				if (key == 'hp' or 
					key == 'attack' or
					key == 'break_power' or
					key == 'magic' or
					key == 'crit_chance' or 
					key == 'speed' or 
					key == 'defense') then
					cargoData[key] = stat[i]
				end
			end
			frame:callParserFunction("#cargo_store:", cargoData)
			mw.logObject(cargoData)
		end
	end
	
	-- Display
	local root = mw.html.create("")
	local wikitable = root:tag("table")
		:addClass("wikitable")
		:cssText("text-align:right;")
		:tag("caption")
			:wikitext(caption)
			:done()
	for i,entry in ipairs(data) do
		if entry.name ~= "???" or i ~= 12 then
			local tagname = entry.type == "header" and "th" or "td"
			local row = wikitable:tag("tr")
			local nameColumn = row:tag("th")
			nameColumn:wikitext(entry.name)
			if i > 1 then
				nameColumn:cssText("text-align:left")
			end
			for _,key in ipairs{1, 2, 3, 4, "mod", 5} do
				row:tag(tagname):wikitext(entry[key] or "-")
			end
		end
	end
	return tostring(root)
end
	
function p.main(frame)
	mArguments = require("Module:Arguments")
	local args = mArguments.getArgs(frame, {
		wrappers = {
			"Template:Weapon stats",
		}
	})
	return p._main(args)
end
	
--[[ Usage:
_main{
	name = "Lightbringer",
	hp = "100, 200, 300, 400",
	atk = "15, 40, 60, 80",
	brk = "10, 20, 30, 40",
	mag = "15, 30, 40, 60",
	crt = "0, 0, 0, 0",
	spd = "0, 1, 1, 1",
	def = "15, 15, 15, 15",
	abi1 = "Piercing Break", val1 = "30, 50, 50, 50", max1 = "100",
	abi2 = "Auto-Charge Ultimate", mod2 = "2", max2 = "8",
	abi3 = "Steelguard", mod3 = "1", max3 = "5",
}
]]
function p.test()
	mw.log(p._main{
		name = "Lightbringer",
		hp = "100, 200, 300, 400",
		atk = "15, 40, 60, 80",
		brk = "10, 20, 30, 40",
		mag = "15, 30, 40, 60",
		crt = "0, 0, 0, 0",
		spd = "0, 1, 1, 1",
		def = "15, 15, 15, 15",
		abi1 = "Piercing Break", val1 = "30, 50, 50, 50", max1 = "100",
		abi2 = "Auto-Charge Ultimate", mod2 = "2", max2 = "8",
		abi3 = "Steelguard", mod3 = "1", max3 = "5",
	})
	mw.log(p._main{
		name = "Arc Mirage",
		hp  = "0, -, -, 0",
		atk = "15, -, -, 55",
		brk = "15, -, -, 55",
		mag = "15, -, -, 60",
		cri = "2, , , 2",
		spd = "0, , , 1",
		def = "0, , , 0",
		abi1 = "Kill & Draw" , val1 = "2,2,2,2" , max1 = "",
		abi2 = "Elemental Third Strike" , val2 = "2,2,2,2" , max2 = "",
	})
end
	
return p