Module:BioboxUnits
Documentation for this module may be created at Module:BioboxUnits/doc
local BioboxUnits = {}
local INCHES_PER_FOOT = 12
local CM_PER_FOOT = 30.48
local CM_PER_INCH = 2.54
local LBS_PER_KG = 2.204623
local function formatDecimal(num)
return string.format("%.1f", num)
end
local function formatCategoryLink(category, display)
return string.format('<span class="white-link">[[:Category:%s|%s]]</span>', category, display)
end
function BioboxUnits.extractNumber(str)
if type(str) == 'number' then return str end
if type(str) ~= 'string' or str == '' then return nil end
local num = tonumber(str)
if num then return num end
num = str:match("^%s*(%d+%.?%d*)[%s%a]*$")
if num then return tonumber(num) end
num = str:match("^%s*(%d+%.?%d*)%a*$")
if num then return tonumber(num) end
num = str:match("^%s*(%d+,%d+)%s*$")
if num then return tonumber(num:gsub(",", ".")) end
return nil
end
function BioboxUnits.cmToFeetInches(cm)
local totalInches = cm / CM_PER_INCH
local feet = math.floor(totalInches / INCHES_PER_FOOT)
local inches = math.floor(totalInches - (feet * INCHES_PER_FOOT))
return feet, inches
end
function BioboxUnits.formatHeight(frame, cm, options)
if type(cm) == 'string' then
cm = BioboxUnits.extractNumber(cm)
end
if not cm or cm == 0 then return "N/A" end
local roundedCm = math.floor(cm)
local feet, inches = BioboxUnits.cmToFeetInches(cm)
local metricPart = formatCategoryLink(
string.format("Height %d cm", roundedCm),
string.format("%s cm", formatDecimal(cm))
)
local imperialPart = formatCategoryLink(
string.format("Height %d cm", roundedCm),
string.format("%d ft %d in", feet, inches)
)
local category = ""
if mw.title.getCurrentTitle().namespace == 0 then
category = string.format("[[Category:Height %d cm]]", roundedCm)
end
return string.format("%s<br>(%s)%s",
metricPart,
imperialPart,
category)
end
function BioboxUnits.formatWeight(frame, kg, options)
if type(kg) == 'string' then
kg = BioboxUnits.extractNumber(kg)
end
if not kg or kg == 0 then return "N/A" end
local roundedKg = math.floor(kg)
local lbs = math.floor(kg * LBS_PER_KG)
local metricPart = formatCategoryLink(
string.format("Weight %d kg", roundedKg),
string.format("%s kg", formatDecimal(kg))
)
local imperialPart = formatCategoryLink(
string.format("Weight %d kg", roundedKg),
string.format("%d lbs", lbs)
)
local category = ""
if mw.title.getCurrentTitle().namespace == 0 then
category = string.format("[[Category:Weight %d kg]]", roundedKg)
end
return string.format("%s<br>(%s)%s",
metricPart,
imperialPart,
category)
end
function BioboxUnits.isValidHeight(value)
local num = BioboxUnits.extractNumber(value)
return num and num > 0 and num < 300
end
function BioboxUnits.isValidWeight(value)
local num = BioboxUnits.extractNumber(value)
return num and num > 0 and num < 500
end
local function toInches(cm)
return cm / CM_PER_INCH
end
local function toCentimeters(inches)
return inches * CM_PER_INCH
end
local function formatPenisSizeNumber(value)
value = math.floor(value * 10 + 0.5) / 10
return value % 1 == 0 and string.format("%.0f", value) or string.format("%.1f", value)
end
local function formatPenisSizeLink(value, unit)
if unit == "in" then
return string.format('[[:Category:Penis size %s inches|%s in]]', value, value)
else
return string.format('[[:Category:Penis size %s cm|%s cm]]', value, value)
end
end
local function applyPenisSizeOption(value, option, tag)
return (option == "yes" or option == "y") and string.format(tag, value) or value
end
function BioboxUnits.formatPenisSize(frame)
local input = frame.args[1] or ""
local categoryOption = frame.args["category"] or "yes"
local breakOption = frame.args["break"] or "no"
local linkspanOption = frame.args["linkspan"] or "no"
input = string.lower(input:gsub("%s+", "")):gsub(",", ".")
local cm, inches
if string.match(input, "in$") or string.match(input, "inches$") then
inches = tonumber(string.match(input, "%d+%.?%d*"))
cm = toCentimeters(inches)
else
cm = tonumber(string.match(input, "%d+%.?%d*"))
if cm == nil then return "" end
inches = toInches(cm)
end
local formattedCm = formatPenisSizeNumber(cm)
local formattedInches = formatPenisSizeNumber(inches)
local linkCm = formatPenisSizeLink(formattedCm, "cm")
local linkInches = formatPenisSizeLink(formattedInches, "in")
linkCm = applyPenisSizeOption(linkCm, linkspanOption, '<span class="white-link">%s</span>')
linkInches = applyPenisSizeOption(linkInches, linkspanOption, '<span class="white-link">%s</span>')
local breakTag = applyPenisSizeOption("", breakOption, "<br>")
if categoryOption == "no" then
return linkCm .. breakTag .. " (" .. linkInches .. ")"
elseif mw.title.getCurrentTitle().namespace == 0 then
return "[[Category:Penis size " .. formattedCm .. " cm]]" .. linkCm .. breakTag .. " (" .. linkInches .. ")" .. "[[Category:Penis size " .. formattedInches .. " inches]]"
else
return linkCm .. breakTag .. " (" .. linkInches .. ")"
end
end
return BioboxUnits