Module:Infobox chord
Note: Do not invoke this module directly; use the corresponding template instead: Template:Infobox chord.
This module implements {{Infobox chord}}
to generate an infobox providing information about a given chord.
local p = {}
local rat = require("Module:Rational")
local utils = require("Module:Utils")
local infobox = require("Module:Infobox")
function p.infobox_chord(frame)
local debug_mode = frame.args["debug"]
local page_name = frame:preprocess("{{PAGENAME}}")
local debug_data = ""
local infobox_data = {}
local cats = ""
local name = frame.args["Name"]
if utils.value_provided(name) then
local caption = "Name"
if name:match(",") then
caption = "Names"
-- removing manual line breaks
local matches
name, matches = name:gsub("<br/?>", "")
if matches > 0 then
cats = cats .. "[[Category:Todo:remove manual line breaks]]"
end
-- removing whitespaces after commas
name = name:gsub(",%s+", ",")
-- placing line breaks after commas
name = name:gsub(",", ",<br/>")
end
table.insert(infobox_data, {
caption,
name,
})
end
if utils.value_provided(frame.args["Harmonics"]) then
local harmonics = {}
for hs in string.gmatch(frame.args["Harmonics"], "[^:]+") do
h = tonumber(hs) -- TODO: support rational entries?
assert(h > 0, "invalid harmonic")
table.insert(harmonics, h)
end
local root = harmonics[1]
if utils.value_provided(frame.args["Root"]) then
root = tonumber(frame.args["Root"])
assert(root > 0, "invalid root")
end
assert(root > 0, "no harmonics given")
local prime_limit = 1
local root_interval_links = {}
for i, h in ipairs(harmonics) do
for prime, n in pairs(utils.prime_factorization_raw(h)) do
if prime > prime_limit then
prime_limit = prime
end
end
local gcd = utils._gcd(h, root)
local numer = h / gcd
local denom = root / gcd
table.insert(root_interval_links, "[[" .. numer .. "/" .. denom .. "|" .. numer .. "⁄" .. denom .. "]]")
end
local odd_limit = 1
for j, b in ipairs(harmonics) do
for i, a in ipairs(harmonics) do
local gcd = utils._gcd(a, b)
local numer = b / gcd
local denom = a / gcd
while numer % 2 == 0 do
numer = numer / 2
end
if numer > odd_limit then
odd_limit = numer
end
while denom % 2 == 0 do
denom = denom / 2
end
if denom > odd_limit then
odd_limit = denom
end
end
end
table.insert(infobox_data, {"Harmonics", frame.args["Harmonics"]})
table.insert(infobox_data, {"Intervals from root", "<big>" .. table.concat(root_interval_links, " ‒ ") .. "</big>"})
if prime_limit < 96 then
table.insert(infobox_data, {"[[Prime limit]]", "[[" .. prime_limit .. "-limit|" .. prime_limit .. "]]"})
cats = cats .. "[[Category:" .. prime_limit .. "-limit chords]]"
else
table.insert(infobox_data, {"[[Prime limit]]", prime_limit})
cats = cats .. "[[Category:Just intonation chords]]"
end
if odd_limit < 32 then
table.insert(infobox_data, {"[[Odd limit]]", "[[" .. odd_limit .. "-odd-limit|" .. odd_limit .. "]]"})
cats = cats .. "[[Category:" .. odd_limit .. "-odd-limit chords]]"
else
table.insert(infobox_data, {"[[Odd limit]]", odd_limit})
end
end
if debug_data ~= "" then
table.insert(infobox_data, {
"Debug",
debug_data,
})
end
local s = infobox.build("<u>Chord information</u>", infobox_data)
if not debug_mode then
s = s .. cats
end
return s
end
return p