Module:TAMNAMS: Difference between revisions

Ganaram inukshuk (talk | contribs)
Remove spaces surrounding pipe for udp as the standard is no spaces
ArrowHead294 (talk | contribs)
mNo edit summary
 
(13 intermediate revisions by 3 users not shown)
Line 1: Line 1:
-- Module for TAMNAMS-related things as it pertains to mosses
local p = {}
-- This module is meant to be used with other modules, not as part of a template
 
local mos = require("Module:MOS")
local mos = require("Module:MOS")
local rat = require("Module:Rational")
local rat = require("Module:Rational")
local p = {}


-- This module should reflect current TAMNAMS standards:
-- TODO
-- - Names for step ratios and ranges (soft, hard, etc)
--Function to parse a UDP and (possibly) scale degrees.
-- - Extended step ratio ranges
--Separate interval/degree lookup into separate functions for for abbrevs and non-abbrev formats.
-- - Naming for intervals and scale degrees (M2ms and M2md)
--Added arbitrary hardness lookup for a single ratio (e.g., passing in 13:8 would return "quasisoft".
-- - Naming for modes (basically UDP)
-- - Naming for select scales


-- TODO?
-- - Function to parse a UDP and (possibly) scale degrees


--------------------------------------------------------------------------------
--------------------------------------------------------------------------------
Line 133: Line 128:
["1L 1s"] = "monwd",
["1L 1s"] = "monwd",
["2L 2s"] = "biwd",
["2L 2s"] = "biwd",
["2L 3s"] = "pent",
["1L 5s"] = "amech",
["1L 5s"] = "amech",
["2L 4s"] = "mal",
["2L 4s"] = "mal",
Line 270: Line 266:
-- Mosses for name lookup are entered either as a scalesig or as a mos as
-- Mosses for name lookup are entered either as a scalesig or as a mos as
-- defined in the mos module. If of the latter, it's converted into a textual
-- defined in the mos module. If of the latter, it's converted into a textual
-- scalesig.
-- scalesig. Scalesigs should have a normal space, not a nonbreaking space, as
-- the lookup tables use a normal space.
function p.preprocess_scalesig(input_mos)
function p.preprocess_scalesig(input_mos)
if type(input_mos) == "string" then
if type(input_mos) == "string" then
return input_mos
local parsed_mos = mos.parse(input_mos)
return mos.as_string(parsed_mos, false)
elseif type(input_mos) == "table" then
elseif type(input_mos) == "table" then
return mos.as_string(input_mos)
return mos.as_string(input_mos, false)
else
else
return nil
return nil
Line 373: Line 371:
local named_ratio_range = use_extended and p.step_ratio_ranges_ext[key] or p.step_ratio_ranges[key]
local named_ratio_range = use_extended and p.step_ratio_ranges_ext[key] or p.step_ratio_ranges[key]
return named_ratio_range
end
--------------------------------------------------------------------------------
------------------------- NAME FINDER FUNCTIONS --------------------------------
--------------------------------------------------------------------------------
-- Helper function
-- "Rounds" step ratios up to the nearest named ratio
function p.step_ratio_ceil(step_ratio)
local hardness = step_ratio[1] / step_ratio[2]
local rounded_step_ratio = nil
if hardness > 1/1 and hardness <= 4/3 then
rounded_step_ratio = {4,3}
elseif hardness > 4/3 and hardness <= 3/2 then
rounded_step_ratio = {3,2}
elseif hardness > 3/2 and hardness <= 5/3 then
rounded_step_ratio = {5,3}
elseif hardness > 5/3 and hardness <= 2/1 then
rounded_step_ratio = {2,1}
elseif hardness > 2/1 and hardness <= 5/2 then
rounded_step_ratio = {5,2}
elseif hardness > 5/2 and hardness <= 3/1 then
rounded_step_ratio = {3,1}
elseif hardness > 3/1 and hardness <= 4/1 then
rounded_step_ratio = {4,1}
elseif hardness > 4/1 and hardness <= 1/0 then
rounded_step_ratio = {1,0}
end
return rounded_step_ratio
end
-- Helper function
-- "Rounds" step ratios down to the nearest named ratio
function p.step_ratio_floor(step_ratio)
local hardness = step_ratio[1] / step_ratio[2]
local rounded_step_ratio = nil
if hardness >= 1/1 and hardness < 4/3 then
rounded_step_ratio = {1,1}
elseif hardness >= 4/3 and hardness < 3/2 then
rounded_step_ratio = {4,3}
elseif hardness >= 3/2 and hardness < 5/3 then
rounded_step_ratio = {3,2}
elseif hardness >= 5/3 and hardness < 2/1 then
rounded_step_ratio = {5,3}
elseif hardness >= 2/1 and hardness < 5/2 then
rounded_step_ratio = {2,1}
elseif hardness >= 5/2 and hardness < 3/1 then
rounded_step_ratio = {5,2}
elseif hardness >= 3/1 and hardness < 4/1 then
rounded_step_ratio = {3,1}
elseif hardness >= 4/1 and hardness < 1/0 then
rounded_step_ratio = {4,1}
end
return rounded_step_ratio
end
-- Function for finding the smallest step ratio range that encompasses the two
-- ratios passed in.
function p.find_step_ratio_range_for_ratio_pair(step_ratio_1, step_ratio_2, use_extended)
local use_extended = use_extended == true -- Does nothing for now
-- Swap ratios so they're in the right order
local hardness_1 = step_ratio_1[1] / step_ratio_1[2]
local hardness_2 = step_ratio_2[1] / step_ratio_2[2]
local lower_ratio = nil
local upper_ratio = nil
local named_ratio_range = ""
if hardness_1 <= hardness_2 then
lower_ratio = p.step_ratio_floor(step_ratio_1)
upper_ratio = p.step_ratio_ceil (step_ratio_2)
else
lower_ratio = p.step_ratio_floor(step_ratio_2)
upper_ratio = p.step_ratio_ceil (step_ratio_1)
end
-- If one ratio corresponds to the endpoint of a named hardness range
-- but the other ratio exceeds that of a smaller range, default to the
-- largest range that would accommodate it.
-- 2:1 to (L:s > 3:1) = hard-of-basic
-- 4:1 and up = ultrahard
-- (L:s < 3:2) to 2:1 = soft-of-basic
-- 4:3 and lower = ultrasoft
if (lower_ratio[1]/lower_ratio[2] == 2/1 and upper_ratio[1]/upper_ratio[2] > 3/1) or lower_ratio[1]/lower_ratio[2] == 4/1 then
upper_ratio = {1,0}
elseif (upper_ratio[1]/upper_ratio[2] == 2/1 and lower_ratio[1]/lower_ratio[2] < 3/2) or upper_ratio[1]/upper_ratio[2] == 4/3 then
lower_ratio = {1,1}
end
local named_ratio_range = p.lookup_step_ratio_range(lower_ratio, upper_ratio, use_extended)
return named_ratio_range
return named_ratio_range
end
end
Line 726: Line 816:
if alterations ~= nil then
if alterations ~= nil then
for i = 1, #alterations do
for i = 1, #alterations do
alterations_as_string = alterations_as_string .. " " .. alterations[i]
alterations_as_string = alterations_as_string .. "&nbsp;" .. alterations[i]
end
end
end
end
if periods == 1 then
 
return string.format("%s&#124;%s", gens_up_per_period, gens_down_per_period) .. alterations_as_string
return (periods == 1
else
and string.format("%s{{pipe}}%s", gens_up_per_period, gens_down_per_period)
return string.format("%s&#124;%s(%s)", gens_up_per_period * periods, gens_down_per_period * periods, periods) .. alterations_as_string
or string.format("%s{{pipe}}%s(%s)", gens_up_per_period * periods, gens_down_per_period * periods, periods))
end
.. alterations_as_string
end
end


Line 867: Line 957:
-- vectors (a table containing the number of L's and s's for that interval).
-- vectors (a table containing the number of L's and s's for that interval).
function p.differences_between_modes(base_step_matrix, altered_step_matrix)
function p.differences_between_modes(base_step_matrix, altered_step_matrix)
local differences = {}
local differences = {}
for i = 1, #altered_step_matrix do
for i = 1, #altered_step_matrix do
Line 905: Line 994:


function p.tester()
function p.tester()
return p.verify_prefix(mos.new(5,3), "")
local input_mos = mos.new(5, 2)
return p.preprocess_scalesig(input_mos)
end
end


return p
return p