Module:gmh-decl-noun


local export = {}

local m_links = require("Module:links")
local m_utils = require("Module:utilities")
local rmatch = mw.ustring.match

local lang = require("Module:languages").getByCode("gmh")

local decl_data = {}

decl_data["a-m"] = {
	params = {
		[1] = {},
		[2] = {},
		[3]= {},
		["alt1"] = {},
		["alt2"] = {},
		["alt3"] = {},
	},
}
setmetatable(decl_data["a-m"], {__call = function(self, args, data)
	data.decl_type = "masculine, a-stem"
	
	local a1 = args.alt1 or args[1]
	local a2 = args.alt2 or args[2] or a1
	local a3 = args.alt3 or args[3] or a2
	
	data.forms["art_ind_nom_sg"] = {"ein"}
	data.forms["art_ind_gen_sg"] = {"eines"}
	data.forms["art_ind_dat_sg"] = {"einem"}
	data.forms["art_ind_acc_sg"] = {"einen"}
	data.forms["art_def_nom_sg"] = {"dër"}
	data.forms["art_def_gen_sg"] = {"dës"}
	data.forms["art_def_dat_sg"] = {"dëm"}
	data.forms["art_def_acc_sg"] = {"dën"}
	data.forms["art_def_nom_pl"] = {"die"}
	data.forms["art_def_gen_pl"] = {"dër"}
	data.forms["art_def_dat_pl"] = {"dën"}
	data.forms["art_def_acc_pl"] = {"die"}

if a2 == "2" then

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a1}
	data.forms["gen_sg"] = {a1 .. "es", a1 .. "s"}
	data.forms["dat_sg"] = {a1 .. "e", a1}


	data.forms["nom_pl"] = {a1 .. "e", a1}
	data.forms["acc_pl"] = {a1 .. "e", a1}
	data.forms["gen_pl"] = {a1 .. "e", a1}
	data.forms["dat_pl"] = {a1 .. "en", a1 .. "n"}

else

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a1}
	data.forms["gen_sg"] = {a2 .. "es"}
	data.forms["dat_sg"] = {a2 .. "e"}

	data.forms["nom_pl"] = {a3 .. "e"}
	data.forms["acc_pl"] = {a3 .. "e"}
	data.forms["gen_pl"] = {a3 .. "e"}
	data.forms["dat_pl"] = {a3 .. "en"}

end
	
end
})

decl_data["i-m"] = {
	params = {
		[1] = {},
		[2] = {},
		[3]= {},
		["alt1"] = {},
		["alt2"] = {},
		["alt3"] = {},
	},
}
setmetatable(decl_data["i-m"], {__call = function(self, args, data)
	data.decl_type = "masculine, i-stem"
	
	local a1 = args.alt1 or args[1]
	local a2 = args.alt2 or args[2] or a1
	local a3 = args.alt3 or args[3] or a2
	
	data.forms["art_ind_nom_sg"] = {"ein"}
	data.forms["art_ind_gen_sg"] = {"eines"}
	data.forms["art_ind_dat_sg"] = {"einem"}
	data.forms["art_ind_acc_sg"] = {"einen"}
	data.forms["art_def_nom_sg"] = {"dër"}
	data.forms["art_def_gen_sg"] = {"dës"}
	data.forms["art_def_dat_sg"] = {"dëm"}
	data.forms["art_def_acc_sg"] = {"dën"}
	data.forms["art_def_nom_pl"] = {"die"}
	data.forms["art_def_gen_pl"] = {"dër"}
	data.forms["art_def_dat_pl"] = {"dën"}
	data.forms["art_def_acc_pl"] = {"die"}

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a1}
	data.forms["gen_sg"] = {a2 .. "es"}
	data.forms["dat_sg"] = {a2 .. "e"}

	data.forms["nom_pl"] = {a3 .. "e"}
	data.forms["acc_pl"] = {a3 .. "e"}
	data.forms["gen_pl"] = {a3 .. "e"}
	data.forms["dat_pl"] = {a3 .. "en"}
	
end
})

decl_data["a-n"] = {
	params = {
		[1] = {},
		[2] = {},
		[3] = {},
		["alt1"] = {},
		["alt2"] = {},
		["alt3"] = {},
	},
}
setmetatable(decl_data["a-n"], {__call = function(self, args, data)
	data.decl_type = "neuter, a-stem"

	local a1 = args.alt1 or args[1]
	local a2 = args.alt2 or args[2] or a1
	local a3 = args.alt3 or args[3] or a2
	

	data.forms["art_ind_nom_sg"] = {"ein"}
	data.forms["art_ind_gen_sg"] = {"eines"}
	data.forms["art_ind_dat_sg"] = {"einem"}
	data.forms["art_ind_acc_sg"] = {"ein"}
	data.forms["art_def_nom_sg"] = {"daȥ"}
	data.forms["art_def_gen_sg"] = {"dës"}
	data.forms["art_def_dat_sg"] = {"dëm"}
	data.forms["art_def_acc_sg"] = {"daȥ"}
	data.forms["art_def_nom_pl"] = {"diu"}
	data.forms["art_def_gen_pl"] = {"dër"}
	data.forms["art_def_dat_pl"] = {"dën"}
	data.forms["art_def_acc_pl"] = {"diu"}

	if rmatch(a2, ".*e$") then

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a1}
	data.forms["gen_sg"] = {a2 .. "s"}
	data.forms["dat_sg"] = {a2}

	data.forms["nom_pl"] = {a1}
	data.forms["acc_pl"] = {a1}
	data.forms["gen_pl"] = {a2}
	data.forms["dat_pl"] = {a2 .. "n"}

elseif a2 == "2" then

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a1}
	data.forms["gen_sg"] = {a1 .. "s"}
	data.forms["dat_sg"] = {a1}

	data.forms["nom_pl"] = {a1}
	data.forms["acc_pl"] = {a1}
	data.forms["gen_pl"] = {a1}
	data.forms["dat_pl"] = {a1 .. "n"} 

elseif args.alt3 or args[3] then

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a1}
	data.forms["gen_sg"] = {a2 .. "es"}
	data.forms["dat_sg"] = {a2 .. "e"}

	data.forms["nom_pl"] = {a3 .. "er"}
	data.forms["acc_pl"] = {a3 .. "er"}
	data.forms["gen_pl"] = {a3 .. "er"}
	data.forms["dat_pl"] = {a3 .. "ern"} 
	
else 

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a1}
	data.forms["gen_sg"] = {a2 .. "es"}
	data.forms["dat_sg"] = {a2 .. "e"}

	data.forms["nom_pl"] = {a1}
	data.forms["acc_pl"] = {a1}
	data.forms["gen_pl"] = {a2 .. "e"}
	data.forms["dat_pl"] = {a2 .. "en"}

end
end
})

decl_data["o-f"] = {
	params = {
		[1] = {},
		["alt1"] = {},
		},
}
setmetatable(decl_data["o-f"], {__call = function(self, args, data)
	data.decl_type = "feminine, ô-stem"
	
	local a1 = args.alt1 or args[1]
	

	data.forms["art_ind_nom_sg"] = {"einiu"}
	data.forms["art_ind_gen_sg"] = {"einer"}
	data.forms["art_ind_dat_sg"] = {"einer"}
	data.forms["art_ind_acc_sg"] = {"eine"}
	data.forms["art_def_nom_sg"] = {"diu"}
	data.forms["art_def_gen_sg"] = {"dër"}
	data.forms["art_def_dat_sg"] = {"dër"}
	data.forms["art_def_acc_sg"] = {"die"}
	data.forms["art_def_nom_pl"] = {"die"}
	data.forms["art_def_gen_pl"] = {"dër"}
	data.forms["art_def_dat_pl"] = {"dën"}
	data.forms["art_def_acc_pl"] = {"die"}

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a1}
	data.forms["gen_sg"] = {a1}
	data.forms["dat_sg"] = {a1}

	data.forms["nom_pl"] = {a1}
	data.forms["acc_pl"] = {a1}
	data.forms["gen_pl"] = {a1 .. "n"}
	data.forms["dat_pl"] = {a1 .. "n"}

end

})

decl_data["i-f"] = {
	params = {
		[1] = {},
		[2] = {},
		["alt1"] = {},
		["alt2"] = {},
		},
}
setmetatable(decl_data["i-f"], {__call = function(self, args, data)
	data.decl_type = "feminine, i-stem"
	
	local a1 = args.alt1 or args[1]
	local a2 = args.alt2 or args[2] or a1
	

	data.forms["art_ind_nom_sg"] = {"einiu"}
	data.forms["art_ind_gen_sg"] = {"einer"}
	data.forms["art_ind_dat_sg"] = {"einer"}
	data.forms["art_ind_acc_sg"] = {"eine"}
	data.forms["art_def_nom_sg"] = {"diu"}
	data.forms["art_def_gen_sg"] = {"dër"}
	data.forms["art_def_dat_sg"] = {"dër"}
	data.forms["art_def_acc_sg"] = {"die"}
	data.forms["art_def_nom_pl"] = {"die"}
	data.forms["art_def_gen_pl"] = {"dër"}
	data.forms["art_def_dat_pl"] = {"dën"}
	data.forms["art_def_acc_pl"] = {"die"}

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a1}
	data.forms["gen_sg"] = {a2 .. "e", a1}
	data.forms["dat_sg"] = {a2 .. "e", a1}

	data.forms["nom_pl"] = {a2 .. "e"}
	data.forms["acc_pl"] = {a2 .. "e"}
	data.forms["gen_pl"] = {a2 .. "e"}
	data.forms["dat_pl"] = {a2 .. "en"}

end

})

decl_data["n-m"] = {
	params = {
		[1] = {},
		[2] = {},
		["alt1"] = {},
		["alt2"] = {},
	},
}
setmetatable(decl_data["n-m"], {__call = function(self, args, data)
	data.decl_type = "masculine, weak"
	
	local a1 = args.alt1 or args[1]
	local a2 = args.alt2 or args[2] or a1
	
	data.forms["art_ind_nom_sg"] = {"ein"}
	data.forms["art_ind_gen_sg"] = {"eines"}
	data.forms["art_ind_dat_sg"] = {"einem"}
	data.forms["art_ind_acc_sg"] = {"einen"}
	data.forms["art_def_nom_sg"] = {"dër"}
	data.forms["art_def_gen_sg"] = {"dës"}
	data.forms["art_def_dat_sg"] = {"dëm"}
	data.forms["art_def_acc_sg"] = {"dën"}
	data.forms["art_def_nom_pl"] = {"die"}
	data.forms["art_def_gen_pl"] = {"dër"}
	data.forms["art_def_dat_pl"] = {"dën"}
	data.forms["art_def_acc_pl"] = {"die"}

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a2 .. "n"}
	data.forms["gen_sg"] = {a2 .. "n"}
	data.forms["dat_sg"] = {a2 .. "n"}

	data.forms["nom_pl"] = {a2 .. "n"}
	data.forms["acc_pl"] = {a2 .. "n"}
	data.forms["gen_pl"] = {a2 .. "n"}
	data.forms["dat_pl"] = {a2 .. "n"}

end

})

decl_data["n-n"] = {
	params = {
		[1] = {},
		[2] = {},
		["alt1"] = {},
		["alt2"] = {},
	},
}
setmetatable(decl_data["n-n"], {__call = function(self, args, data)
	data.decl_type = "neuter, weak"
	
	local a1 = args.alt1 or args[1]
	local a2 = args.alt2 or args[2] or a1
	

	data.forms["art_ind_nom_sg"] = {"ein"}
	data.forms["art_ind_gen_sg"] = {"eines"}
	data.forms["art_ind_dat_sg"] = {"einem"}
	data.forms["art_ind_acc_sg"] = {"ein"}
	data.forms["art_def_nom_sg"] = {"daȥ"}
	data.forms["art_def_gen_sg"] = {"dës"}
	data.forms["art_def_dat_sg"] = {"dëm"}
	data.forms["art_def_acc_sg"] = {"daȥ"}
	data.forms["art_def_nom_pl"] = {"diu"}
	data.forms["art_def_gen_pl"] = {"dër"}
	data.forms["art_def_dat_pl"] = {"dën"}
	data.forms["art_def_acc_pl"] = {"diu"}

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a1}
	data.forms["gen_sg"] = {a2 .. "n"}
	data.forms["dat_sg"] = {a2 .. "n"}

	data.forms["nom_pl"] = {a2 .. "n"}
	data.forms["acc_pl"] = {a2 .. "n"}
	data.forms["gen_pl"] = {a2 .. "n"}
	data.forms["dat_pl"] = {a2 .. "n"}
	
	table.insert(data.categories, "Old High German n-stem nouns")
end
})

decl_data["n-f"] = {
	params = {
		[1] = {},
		[2] = {},
		["alt1"] = {},
		["alt2"] = {},
		},
}
setmetatable(decl_data["n-f"], {__call = function(self, args, data)
	decl_data["n-m"](args, data)
	data.decl_type = "feminine, weak"
	
	local a1 = args.alt1 or args[1]
	local a2 = args.alt2 or args[2] or a1
	

	data.forms["art_ind_nom_sg"] = {"einiu"}
	data.forms["art_ind_gen_sg"] = {"einer"}
	data.forms["art_ind_dat_sg"] = {"einer"}
	data.forms["art_ind_acc_sg"] = {"eine"}
	data.forms["art_def_nom_sg"] = {"diu"}
	data.forms["art_def_gen_sg"] = {"dër"}
	data.forms["art_def_dat_sg"] = {"dër"}
	data.forms["art_def_acc_sg"] = {"die"}
	data.forms["art_def_nom_pl"] = {"die"}
	data.forms["art_def_gen_pl"] = {"dër"}
	data.forms["art_def_dat_pl"] = {"dën"}
	data.forms["art_def_acc_pl"] = {"die"}

	data.forms["nom_sg"] = {a1}
	data.forms["acc_sg"] = {a2 .. "n"}
	data.forms["gen_sg"] = {a2 .. "n"}
	data.forms["dat_sg"] = {a2 .. "n"}

	data.forms["nom_pl"] = {a2 .. "n"}
	data.forms["acc_pl"] = {a2 .. "n"}
	data.forms["gen_pl"] = {a2 .. "n"}
	data.forms["dat_pl"] = {a2 .. "n"}

end
})

-- The main entry point.
-- This is the only function that can be invoked from a template.
function export.show(frame)

	local parent_args = frame:getParent().args
	local decl_type = (frame.args["decl"] or parent_args["decl"]) or "a-m"

	if not decl_data[decl_type] then
		error("Unknown declension '" .. decl_type .. "'")
	end
	
	local data = {forms = {}, categories = {}}
	
	data.head = parent_args["head"] or nil

	local args = require("Module:parameters").process(parent_args, decl_data[decl_type].params, true)
	
	-- Override for templates
	if not args[1] then
		setmetatable(args, {__index = function(self, key)
			return "{{{" .. key .. "}}}"
		end
		})
	end
	
	-- Generate the forms
	if parent_args.irr then
		table.insert(data.categories, "Old High German irregular nouns")
		if decl_data.irregular[parent_args.irr] then
			decl_data.irregular[parent_args.irr](data)
		else
			decl_data[decl_type](args, data)
		end
	else
		decl_data[decl_type](args, data)
	end

	-- Make the table
	return make_table(data)
end

function make_table(data)
	local function show_form(form)
		if not form then
			return "—"
		end
		
		local ret = {}
		
		for key, subform in ipairs(form) do
			if mw.title.getCurrentTitle().nsText == "Reconstruction" and subform ~= "—" then
				subform = "*" .. subform
			end
			table.insert(ret, m_links.full_link({lang = lang, term = subform}))
		end
			
		return table.concat(ret, ", ")
	end
	
	local function repl(param)
		if param == "decl_type" then
			return data.decl_type
		else
			return show_form(data.forms[param])
		end
	end

	local wikicode = [=[<div class="NavFrame" style="width:30em">
<div class="NavHead" style="">Declension of {{{nom_sg}}} ({{{decl_type}}})</div>
<div class="NavContent">

{| style="background:#F9F9F9;text-align:center;width:30em" class="inflection-table" border="1px solid #505050"
|-
! style="background:#AAB8C0" |
! colspan="3" style="background:#AAB8C0" | singular
! colspan="2" style="background:#AAB8C0" | plural
|-
! style="background:#BBC9D0" |
! style="background:#BBC9D0" | [[indefinite article|indef.]]
! style="background:#BBC9D0" | [[definite article|def.]]
! style="background:#BBC9D0" | noun
! style="background:#BBC9D0" | [[definite article|def.]]
! style="background:#BBC9D0" | noun
|-
! style="background:#BBC9D0" | nominative
| style="background:#EEEEEE" | {{{art_ind_nom_sg}}}
| style="background:#EEEEEE" | {{{art_def_nom_sg}}}
| {{{nom_sg}}}
| style="background:#EEEEEE" | {{{art_def_nom_pl}}}
| {{{nom_pl}}}
|-
! style="background:#BBC9D0" | genitive
| style="background:#EEEEEE" | {{{art_ind_gen_sg}}}
| style="background:#EEEEEE" | {{{art_def_gen_sg}}}
| {{{gen_sg}}}
| style="background:#EEEEEE" | {{{art_def_gen_pl}}}
| {{{gen_pl}}}
|-
! style="background:#BBC9D0" | dative
| style="background:#EEEEEE" | {{{art_ind_dat_sg}}}
| style="background:#EEEEEE" | {{{art_def_dat_sg}}}
| {{{dat_sg}}}
| style="background:#EEEEEE" | {{{art_def_dat_pl}}}
| {{{dat_pl}}}
|-
! style="background:#BBC9D0" | accusative
| style="background:#EEEEEE" | {{{art_ind_acc_sg}}}
| style="background:#EEEEEE" | {{{art_def_acc_sg}}}
| {{{acc_sg}}}
| style="background:#EEEEEE" | {{{art_def_acc_pl}}}
| {{{acc_pl}}}
]=]

	wikicode = wikicode .. "|}</div></div>"

	return (mw.ustring.gsub(wikicode, "{{{([a-z0-9_]+)}}}", repl)) .. m_utils.format_categories(data.categories, lang)
end

return export