Module:xchc-pron



local sub = mw.ustring.sub
local find = mw.ustring.find
local gmatch = mw.ustring.gmatch
local gsub = mw.ustring.gsub
local match = mw.ustring.match
local u = mw.ustring.char
local split = mw.text.split
local gsplit = mw.text.gsplit

local M = u(0x0304) -- COMBINING MACRON
local B = u(0x0306) -- COMBINING BREVE
local D = u(0x0308) -- COMBINING DIAERESIS

local lang = require("Module:languages").getByCode("xchc")
local m_IPA = require("Module:IPA")

local consonants = "[mnŋɲptbdkɡfvszʃʒxɣhʧʦʤʣlrɾʎ]"

local export = {}

local function laxen(v)
	local otc = {}
	local switch = {["e"] = "ɛ", ["i"] = "ɪ", ["o"] = "ɔ", ["u"] = "ʊ"}
		 
	for vc in gmatch(v, ".") do
		if switch[vc] then vc = gsub(vc, vc, switch[vc]) end
		table.insert(otc, vc)
	end
	return table.concat(otc)
end

local function same(foo, bar)
	foo, bar = mw.ustring.toNFD(foo), mw.ustring.toNFD(bar) -- decompose diacritics
	foo, bar = match(foo, "^."), match(bar, "^.") -- sort out the letter
	return foo == bar and true or false
end

local first_rules = {
	{"%-", ""}, {M, "ː"}, {"ː([" .. M .. D .. B .. "])", "%1ː"},
	
	{"е" .. D, "ьo"}, {"о" .. B, "ɔ"}, {"э" .. B, "ɛ"}, {"и" .. B, "j"},
	
	{"а", "a"},
	{"б", "b"},
	{"в", "v"},
	{"г", "ɡ"},
	{"ғ", "ɣ"},
	{"дз", "ʣ"}, {"дж", "ʤ"}, {"д", "d"},
	{"е", "ьe"},
	{"ж", "ʒ"},
	{"з", "z"},
	{"и", "ьi"},
	{"к", "k"},
	{"л", "l"},
	{"м", "m"},
	{"н", "n"},
	{"ӈ", "ŋ"},
	{"о", "o"},
	{"ө", "ø"},
	{"п", "p"},
	{"р", "r"},
	{"т", "t"},
	{"с", "s"},
	{"у", "u"},
	{"ү", "y"},
	{"ф", "f"},
	{"[хx]ӏ", "h"}, {"х", "x"},
	{"ц", "ʦ"},
	{"ч", "ʧ"},
	{"ш", "ʃ"},
	{"ы", "i"},
	{"э", "e"},
	{"ю", "ьu"},
	{"я", "ьa"},
	
	{"l[ьі]", "ʎ"}, {"n[ьі]", "ɲ"}, {"[ьі]", "j"},
	
	{"(" .. consonants .. ")(" .. consonants .. ")", function(c1,c2) return same(c1, c2) and c1 .. "ː" or c1 .. c2 end}
}

local last_rules = {
	{"ʣ", "d͡z"},
	{"ʤ", "d͡ʒ"},
	{"ʦ", "t͡s"},
	{"ʧ", "t͡ʃ"},
}

function export.crux(term)
	term = mw.ustring.lower(mw.ustring.toNFD(term))
	
	for _, rule in ipairs(first_rules) do
		term = gsub(term, rule[1], rule[2])
	end
	
	for _, rule in ipairs(last_rules) do
		term = gsub(term, rule[1], rule[2])
	end
	
	return term
end

function export.harmony(term)
	local ipa = export.crux(term)
	local ret = {
		["roundness"] = ipa:match("[yuøo]") and "r" or ipa:match("[ie]") and "u" or "ar",
		["backness"] = ipa:match("ɜ") and "f" or ipa:match("ɔ") and "b" or "ab",
	}
	return ret
end

function separate_word(term)
	local result = {}
	
	for word in gsplit(term, " ") do
		table.insert(result, export.crux(word))
	end
	
	return table.concat(result, " ")
end

function export.show(frame)
	local parent_args = frame:getParent().args
	local params = {
		[1] = { default = mw.title.getCurrentTitle().nsText == 'Template' and "чы̄ӈымэ̆ц" or mw.title.getCurrentTitle().text },
	}
	local args = require("Module:parameters").process(parent_args, params)
	local term = args[1]

	local IPA_args = {}
	local phonetic = separate_word(term)
	table.insert(IPA_args, {pron = '[' .. phonetic .. ']'})

	return "* " .. m_IPA.format_IPA_full(lang, IPA_args)
end

return export