Jump to content

Module:Shindo

Permanently protected module
From Wikipedia, the free encyclopedia

local p = {}
local getArgs = require("Module:Arguments").getArgs
local data = mw.loadData("Module:Shindo/data")
local messages = mw.loadData("Module:Shindo/messages")
local makeInvokeFunc = require("Module:MakeInvokeFunc")(p)
local message = require("Module:Message")(messages)
local yn = require("Module:Yesno")

local function getValueOfColor(tbl)
	return (tbl[1] + tbl[2] + tbl[3]) / 3 / 255
end

local function rgbColor(tbl)
	return tbl[1] .. (tbl[2] and ", " .. tbl[2] .. (tbl[3] and ", " .. tbl[3] or "") or "")
end

local function averageColor(tbl)
	local colors = {}
	for k,v in pairs(tbl) do
		colors[k] = v
	end
	local avg = {0, 0, 0}
	for _,color in pairs(colors) do
		avg[1] = avg[1] + color[1]
		avg[2] = avg[2] + color[2]
		avg[3] = avg[3] + color[3]
	end
	avg[1] = math.ceil(avg[1] / #colors) - avg[1] / #colors > 0.5 and math.floor(avg[1] / #colors) or math.ceil(avg[1] / #colors)
	avg[2] = math.ceil(avg[2] / #colors) - avg[2] / #colors > 0.5 and math.floor(avg[2] / #colors) or math.ceil(avg[2] / #colors)
	avg[3] = math.ceil(avg[3] / #colors) - avg[3] / #colors > 0.5 and math.floor(avg[3] / #colors) or math.ceil(avg[3] / #colors)
	return avg
end

local function listIntensitiesFromScale(scale, intensities, labelScale, scale2)
	local out = ''
	if yn(labelScale) then
		out = out .. data[scale].short .. ' '
	end
	local categoriesAreSame = true
	local category = ""
	for k,v in pairs(intensities) do
		if data[scale].ranks[v] == nil then error(message("invalidIntensity", {v, scale})) end
		out = out .. data[scale].ranks[v].label
		if k ~= #intensities then
			if #intensities == 2 then
				out = out .. '–'
			else
				out = out .. '/'
			end
		end
		if category == "" and categoriesAreSame then
			category = data[scale].ranks[v].category or ""
		end
		categoriesAreSame = categoriesAreSame and category ~= "" and (data[scale].ranks[v].category and data[scale].ranks[v].category == category or false)
	end
	if categoriesAreSame and category ~= "" and not scale2 then
		out = out .. " (''" .. category .. "'')"
	end
	return out
end

p._color = function(args)
	local scale = string.lower(args.scale or args[1] or error(message("noScaleShortCode")))
	local intensity = string.upper(args.intensity or args[2] or error(message("noIntensity")))
	if data[scale] == nil then error(message("invalidScale", {scale})) end
	if data[scale].ranks[intensity] == nil then error(message("invalidIntensity", {intensity, scale})) end
	local order = data[scale].ranks[intensity].order
	local color = data[scale].colors[order]
	local colorIntensity = getValueOfColor(color)
	return 'background-color:rgb(' .. rgbColor(color) .. '); color:' .. (colorIntensity < 0.5 and "white" or "black") .. ";"
end

p._formatInWikitable = function(args)
	local scale = string.lower(args.scale or args[1] or error(message("noScaleShortCode")))
	local link = args.link ~= nil and args.link or true
	local labelScale = args.labelScale ~= nil and args.labelScale or true
	local doColor = args.color ~= nil and args.color or true
	local intensity = string.upper(args.intensity or args[2] or error(message("noIntensity")))
	local intensities = mw.text.split(intensity, "/") or { intensity }
	if data[scale] == nil then error(message("invalidScale", {scale})) end
	local colors = {}
	for k,v in pairs(intensities) do
		local order = data[scale].ranks[v].order
		colors[k] = data[scale].colors[order]
	end
	local color = averageColor(colors)
	local colorIntensity = getValueOfColor(color)
	local out = ""
	if yn(args.header or false) then
		out = out .. "! " 
	else
		out = out .. "| "
	end
	out = out .. (args.tagProps ~= nil and args.tagProps or "")
	if (yn(doColor)) then
		out = out .. 'style="background-color:rgba(' .. rgbColor(color) .. '); color:' .. (colorIntensity < 0.5 and "white" or "black") .. ';' .. (args.style or "") .. '" | '
	elseif (args.style) then
		out = out .. 'style="' .. (args.style or "") .. '" | '
	end
	if yn(link) then
		out = out .. '[[' .. data[scale].name .. "#" .. data[scale].id_prefix .. data[scale].ranks[intensity].id .. "|"
	end
	if yn(doColor) then
		out = out .. '<span style=\"color:' .. (colorIntensity < 0.5 and "white" or "black") .. ';">'
	end
	out = out .. listIntensitiesFromScale(scale, intensities, labelScale, false)
	if yn(doColor) then
		out = out .. '</span>'
	end
	if yn(link) then
		out = out .. "]]"
	end
	return out
end

p._formatTag = function(args)
	local scale = string.lower(args.scale or args[1] or error(message("noScaleShortCode")))
	local scale2 = args.scale2 or args[3] or nil
	if scale2 ~= nil then scale2 = string.lower(scale2) end
	local link = args.link ~= nil and args.link or true
	local labelScale = args.labelScale ~= nil and args.labelScale or true
	local doColor = args.color ~= nil and args.color or true
	local intensity = string.upper(args.intensity or args[2] or error(message("noIntensity")))
	local intensities = mw.text.split(intensity, "/") or { intensity }
	local intensity2 = args.intensity2 or args[4] or (scale2 and error(message("noIntensity"))) or nil
	local intensities2 = {}
	if intensity2 ~= nil then
		intensity2 = string.upper(intensity2)
		intensities2 = mw.text.split(intensity2, "/") or { intensity2 }
	end
	if data[scale] == nil then error(message("invalidScale", {scale})) end
	if scale2 and data[scale2] == nil then error(message("invalidScale", {scale2})) end
	local colors = {}
	for k,v in pairs(intensities) do
		local order = data[scale].ranks[v].order
		colors[k] = data[scale].colors[order]
	end
	local color = averageColor(colors)
	local colorIntensity = getValueOfColor(color)
	local out = ''
	if yn(doColor) then
		out = out .. '<' .. (args.tag or "span") .. ' style="background-color:rgba(' .. rgbColor(color) .. '); padding:4px; color:' .. (colorIntensity < 0.5 and "white" or "black") ..  '; '
	elseif args.style then
		out = out .. '<' .. (args.tag or "span") .. ' style="'
	else
		out = out .. '<' .. (args.tag or "span")
	end
	if args.style then
		out = out .. args.style
		out = out .. '" '
	elseif yn(doColor) then
		out = out .. '" '
	end
	out = out .. (args.tagProps ~= nil and args.tagProps or "")
	out = out .. ">"
	if yn(link) then
		out = out .. '[[' .. data[scale].name .. "#" .. data[scale].id_prefix .. data[scale].ranks[intensities[1]].id .. "|"
	end
	if yn(doColor) then
		out = out .. '<span style=\"color:' .. (colorIntensity < 0.5 and "white" or "black") .. ';">'
	end
	out = out .. listIntensitiesFromScale(scale, intensities, labelScale, scale2)
	if yn(doColor) then
		out = out .. '</span>'
	end
	if yn(link) then
		out = out .. "]]"
	end
	if (scale2) then
		out = out .. " ("
		if yn(link) then
			out = out .. '[[' .. data[scale2].name .. "#" .. data[scale2].id_prefix .. data[scale2].ranks[intensities2[1]].id .. "|"
		end
		if yn(doColor) then
			out = out .. '<span style=\"color:' .. (colorIntensity < 0.5 and "white" or "black") .. ';">'
		end
		out = out .. listIntensitiesFromScale(scale2, intensities2, true, true)
		if yn(doColor) then
			out = out .. '</span>'
		end
		if yn(link) then
			out = out .. "]]"
		end
		out = out .. ")"
	end
	out = out .. '</'  .. (args.tag or "span") .. '>'
	return mw.getCurrentFrame():preprocess(out)
end

p._format = function(args)
	if args["format"] == "wikitable" then
		return p.formatInWikitable(args)
	else
		return p.formatTag(args)
	end
end

p._getScaleName = function(args)
	local scale = string.lower(args.scale or args[1] or error(message("noScaleShortCode")))
	if data[scale] == nil then error(message("invalidScale", {scale})) end
	local out = ''
	if yn(args.link or true) then
		out = out .. '[[' .. data[scale].name .. '|'
	end
	out = out .. data[scale].name
	if yn(args.link or true) then
		out = out .. ']]'
	end
	return out
end

-- uses binary search to convert a peak ground acceleration to a seismic intensity
function convert(pga, ranks, ranksSorted, left, right)
	left = left ~= nil and left or 0
	right = right ~= nil and right or #ranksSorted
	index = math.floor((left + right) / 2)
	local lower = ranks[ranksSorted[index + 1]].pga
	local upper = ranksSorted[index + 2] and ranks[ranksSorted[index + 2]].pga or math.huge
	if (pga >= upper) then
		return convert(pga, ranks, ranksSorted, index, right)
	elseif (pga < lower) then
		return convert(pga, ranks, ranksSorted, left, index)
	else
		return ranksSorted[index + 1]
	end
end

p._convert = function(args)
	local scale = string.lower(args.scale or args[1] or error(message("noScaleShortCode")))
	if data[scale] == nil then error(message("invalidScale", {scale})) end
	local ranksSorted = {}
	for k,v in ipairs(data["mmi"].ranksSorted) do ranksSorted[k] = v end
	return convert(tonumber(args.pga or args[2]), data[scale].ranks, ranksSorted)
end

p.convert1 = convert --debugging

p._list = function(args)
	local out = mw.html.create('ul')
	for k,v in pairs(data) do
		local list = out:tag('li')
		list:wikitext('<code>' .. k .. '</code>: [[' .. v.name .. '|' .. v.name .. ']]')
		local tb = list:tag('table'):addClass("wikitable")
		tb
			:tag("tr")
				:tag("th"):wikitext("Seismic intensity"):done()
				:tag("th"):wikitext("Display"):done()
			:done()
		for l,w in pairs(v.order) do
			tb:tag('tr'):wikitext('<td><code>' .. w .. '</code></td> ' .. p.format({k, w, tag = "td"})):done()
		end
		list:done()
	end
	out:allDone()
	return tostring(out)
end

-- make each scale invokable
for k,v in pairs(data) do
	if p["_" .. k] ~= nil then error(message("scaleNameInvalid", k)) end
	p["_" .. k] = function(args)
		args["scale"] = k
		args["intensity"] = args["intensity"] or args[1] or nil
		args["scale2"] = args["scale2"] or args[2] or nil
		args["intensity2"] = args["intensity2"] or args[3] or nil
		if args["format"] == "wikitable" then
			return p.formatInWikitable(args)
		else
			return p.formatTag(args)
		end
	end
end

-- make all functions that begin with _ invokable
local q = mw.clone(p)
for k,v in pairs(q) do
	if mw.ustring.sub(k, 1, 1) == "_" then
		p[mw.ustring.sub(k, 2, #k)] = makeInvokeFunc(k)
	end
end

return p
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy