Module:Other Languages
From The Petit Planet Wiki
More actions
Documentation for this module may be created at Module:Other Languages/doc
local p = {}
local lib = require('Module:Feature')
local KOrm = require('Module:Ko-rm')
local i18n = require('Module:I18n').loadMessages('Other Languages')
local SelectiveSpan = require('Module:Lang').SelectiveSpan
local search = lib.inArray
local ne = lib.isNotEmpty
local ie = lib.isEmpty
local langOrder = {'en', 'zhs', 'zht', 'ja', 'ko', 'es', 'fr', 'ru', 'th', 'vi', 'de', 'id', 'pt', 'tr', 'it'}
local categories = mw.html.create()
local noCat = {}
local Notes = {reuse={}}
function p.main(frame)
local args = require('Module:Arguments').getArgs(frame, {
parentFirst = true,
removeBlanks = false,
wrappers = {'Template:Other Languages'}
})
if ne(args['Transclude']) then
local new_index = lib.split(args['Transclude'], '#')
local transclude = lib.split(new_index[1], ';')
p.Transclude(args, transclude[1], transclude[2], new_index[2])
else
local Y = 1
while ne(args['Transclude_' .. tostring(Y)]) or ne(args[Y]) do
local new_index = lib.split((args['Transclude_' .. tostring(Y)] or args[Y]), '#')
local transclude = lib.split(new_index[1], ';')
p.Transclude(args, transclude[1], transclude[2], new_index[2])
Y = Y + 1
end
end
p.ParseNotes(args)
return p._main(args, frame)
end
--- Entry point for other modules.
-- @param args The table of arguments for which to generate an HTML table
-- @param frame Optional argument to specify a frame, which will be used for its extensionTag.
-- If not specified, the current frame will be used.
function p._main(args, frame)
local out
if ne(args['1_en']) then
categories:wikitext('[[Category:Other Languages with Multiple Tables]]')
out = mw.html.create('div'):css{['display']='flex', ['column-gap'] = '15px', ['flex-direction'] = 'row', ['flex-wrap'] = 'wrap'}
local Y = 1
local y = tostring(Y)
while args[y .. '_en'] do
local entry = out:tag('div')
entry:tag('h3'):wikitext(args[y .. '_header'] or args[y .. '_en'])
entry:node(p.Table(args, frame, (y .. '_')))
--continue loop
Y = Y+1
y = tostring(Y)
end
else
out = p.Table(args, frame)
end
return tostring(out:node(require('Module:Namespace detect').main{["main"]=categories})) .. (not args.noref and frame:extensionTag{ name = 'references', args = { group = '•' } } or '')
end
function p.Table(args, frame, prefix)
prefix = prefix or ''
local TLcol = false
--[[list of all lang codes and some settings used in the loop
['lang_code'] = {
rm = setting for the loop to check if lang should have rm,
span = lang code to use in the transcript span if different from base lang code
}
--]]
local lang = {
['zhs'] = { rm = true, span = 'zh-Hans' },
['zht'] = { rm = true, span = 'zh-Hant' },
['ja'] = { rm = true },
['ko'] = { rm = true },
['ru'] = { rm = true },
['th'] = { rm = true }
}
--initialize the table in html syntax and the category variable
local articletable = mw.html.create('table'):addClass('article-table'):newline()
--header row
local tr = articletable:tag('tr')
tr:tag('th'):wikitext('Language')
tr:tag('th'):wikitext(args.name or 'Official Name')
--check if any [lang]_tl exists to show tl column if true
local validTable = false
for _, langCode in ipairs(langOrder) do
if ne(args[prefix .. langCode]) then
if langCode ~= 'en' then validTable = true end
if args[prefix .. 'default_hidden'] or args['default_hidden'] then
if ((ne(args[prefix .. langCode .. '_tl']) or ne(args[prefix .. 'zh_tl'])) and TLcol == false) then
tr:tag('th'):wikitext('Literal Meaning')
TLcol = true
end
else
if ((args[prefix .. langCode .. '_tl'] or args[prefix .. 'zh_tl']) and TLcol == false) then
tr:tag('th'):wikitext('Literal Meaning')
TLcol = true
end
end
end
end
if not validTable then categories:wikitext('[[Category:Empty Other Languages]]') end
--start loop to create the lang rows with langOrder as iterator list to determine the order of the rows
for i, langCode in ipairs(langOrder) do
--variables for ease of use
local Tx = args[prefix .. langCode] or nil
local Tl = args[prefix .. langCode .. '_tl'] or nil
local Rm = args[prefix .. langCode .. '_rm'] or nil
local Loanword = args[prefix .. langCode .. '_lang'] or nil
local Loanword_Tl = args[prefix .. langCode .. '_lang_tl'] or nil
local Note = args[prefix .. langCode .. '_note'] or nil
local Lang = lang[langCode] or {}
--default to pagename if en transcript is not given
if langCode == 'en' then
if Tx then if ie(Tx) then Tx = mw.title.getCurrentTitle().text end else Tx = mw.title.getCurrentTitle().text end
end
--do a check for if transcript for the lang exists and is not blank, move on to next lang if false
if Tx then
if ie(Tx) then
if not noCat[prefix .. langCode] then
categories:wikitext('[[Category:Incomplete Transcripts for Other Languages]][[Category:',string.upper(langCode),' Transcript Missing]]')
end
elseif Tx == '_UNAVAILABLE' then
if not noCat[prefix .. langCode] then
categories:wikitext('[[Category:Unavailable Transcripts for Other Languages]][[Category:',string.upper(langCode),' Unavailable Transcripts]]')
end
else
local tr = articletable:tag('tr')
--open and close "Language" column cell with value and open "Official Name" column cell with transcript
tr:tag('td'):wikitext(i18n:msg(langCode))
local td = tr:tag('td')
local displayTx = Tx
if langCode == 'zhs' or langCode == 'zht' or langCode == 'ja' then
displayTx = Tx
:gsub('·', '・') -- convert halfwidth middle dot to fullwidth middle dot
elseif langCode == 'ko' then
displayTx = KOrm.strip(Tx) -- strip TX from keywords used in Module:Ko-rm
:gsub('·', '・') -- convert halfwidth middle dot to fullwidth middle dot
elseif langCode == 'fr' then
displayTx = Tx
:gsub(' !', ' !') -- add after/before punctuation so it does not break from the text it relates to
:gsub(' %?', ' ?') --
:gsub(' :', ' :') --
:gsub(' ~', ' ~') --
:gsub(' %-', ' -') --
:gsub(' &', ' &') --
:gsub(' »', ' »') --
:gsub('« ', '« ') --
elseif langCode == 'ru' then
displayTx = p.ruBreak(Tx) -- add <wbr> after hyphens as chromium based browsers do not support Russian properly
elseif langCode == 'th' then
displayTx = Tx
:gsub('%.%.%.', '...<wbr>') -- add <wbr> after ellipses as they do not break properly due to not spacing in Thai, making scroll horizontally
elseif langCode == 'de' then
displayTx = Tx
:gsub('%.%.%.', '...<wbr>') -- add <wbr> after ellipses as they do not break properly due to not spacing in German, making scroll horizontally
end
local code = Lang.span or langCode
td:node(SelectiveSpan(displayTx,code,(code == 'vi' and true or false)))
--lang notes next to transcript if corresponding translation parameter is blank or translation column is not shown
--general lang note
if ((ie(Tl) and TLcol) or TLcol == false) then
for _, ref in ipairs(Notes) do
if ref.langs[prefix .. langCode] then
td:wikitext( frame:extensionTag{ name = 'ref', content = ref.ref, args = { name = prefix .. ref.langs.name, group = '•' } } )
end
end
if Notes.reuse[prefix .. langCode] then
td:wikitext( frame:extensionTag{ name = 'ref', args = { name = Notes.reuse[prefix .. langCode], group = '•' } } )
end
end
-- romanization section
if Lang.rm then
--automatic russian romanization through [[Module:Ru-rm]]
if langCode == 'ru' then
local ru_rm = p.CleanTT(mw.text.unstrip(Tx))
ru_rm = require('Module:Ru-rm')._main{ru_rm}
--display romanization only if it differs from transcript
if p.CleanTT(mw.text.unstrip(Tx)) ~= ru_rm then
td:wikitext('<br />'):tag('small'):tag('i'):wikitext(ru_rm)
end
--automatic korean romanization through [[Module:Ko-rm]]
elseif langCode == 'ko' then
local ko_rm = p.CleanTT(mw.text.unstrip(Tx))
local ko_mode = args.ko_mode or '1'
--if manual rm exists, use it, otherwise automatic, and add category if param exists but no manual rm was given
if ko_mode == '2' then
--debug mode, **DO NOT SAVE WITH THIS SETTING, ONLY PREVIEW**
mw.logObject(Tx, 'Raw tx')
mw.logObject(ko_rm, 'Input to ko_rm')
ko_rm = KOrm._main{ko_rm, capi = 1, nn = args[prefix .. 'ko_nn'] or nil, ni = args[prefix .. 'ko_ni'] or nil, bcred = args[prefix .. 'ko_bcred'] or nil}
td:wikitext('<br />Auto-Rm: ['):tag('small'):tag('i'):wikitext(ko_rm):done():wikitext(']')
td:wikitext('<br />Manual-Rm: ['):tag('small'):tag('i'):wikitext((Rm or '')):done():wikitext(']')
elseif (Rm and ne(Rm) and ko_mode == '1') then
td:wikitext('<br />'):tag('small'):tag('i'):wikitext(Rm)
elseif ko_mode == '1' then
ko_rm = KOrm._main{ko_rm, capi = 1, nn = args[prefix .. 'ko_nn'] or nil, ni = args[prefix .. 'ko_ni'] or nil, bcred = args[prefix .. 'ko_bcred'] or nil}
if Rm == '' and not noCat[prefix .. 'ko_rm'] then categories:wikitext('[[Category:KO Romanization Missing]]') end
--display romanization only if it differs from transcript
if mw.text.unstrip(Tx) ~= ko_rm then
td:wikitext('<br />'):tag('small'):tag('i'):wikitext(ko_rm)
end
end
if Rm ~= nil then
ko_rm2 = require('Module:Ko-rm')._main{ko_rm, capi = 1, nn = args[prefix .. 'ko_nn'] or nil, ni = args[prefix .. 'ko_ni'] or nil, bcred = args[prefix .. 'ko_bcred'] or nil}
if not noCat[prefix .. 'ko_rm'] and ne(Rm) then
if Rm == ko_rm2 then
categories:wikitext('[[Category:Korean Manual Romanization Matches Automatic]]')
else
categories:wikitext('[[Category:Korean Manual Romanization Mismatches Automatic]]')
end
end
end
--automatic korean romanization through [[Module:Ja-rm]]
elseif langCode == 'ja' then
local ja_rm = p.CleanTT(mw.text.unstrip(Tx))
ja_rm = require('Module:Ja-rm')._main{ja_rm, errorcat=true}
if ne(Rm) then
-- manual rm
td:wikitext('<br />'):tag('small'):tag('i'):wikitext(Rm)
if ja_rm ~= '' then
categories:wikitext(
'[[Category:Japanese Manual Romanization ',
lib.ternary(string.lower(Rm):gsub('[%s%-\']', '') == string.lower(ja_rm):gsub('%[%[category:.+$', ''):gsub('[%s%-\']', ''), 'Matches', 'Mismatches'),
' Automatic]]'
)
end
elseif ja_rm ~= '' and ja_rm~=Tx then
-- valid automatic rm
td:wikitext('<br />'):tag('small'):tag('i'):wikitext(ja_rm)
end
if ja_rm == '' and Rm == '' and not noCat[prefix .. 'ja_rm'] then categories:wikitext('[[Category:JA Romanization Missing]]') end
elseif Rm and (langCode == 'zhs' or langCode == 'zht') then
td:wikitext('<br />'):tag('small'):tag('i'):tag('span'):attr('lang', 'zh-rm'):wikitext(Rm)
if ie(Rm) and not noCat[prefix .. langCode .. '_rm'] then categories:wikitext('[[Category:',string.upper(langCode),' Romanization Missing]]') end
--general romanization inclusion
elseif Rm then
td:wikitext('<br />'):tag('small'):tag('i'):wikitext(Rm)
if ie(Rm) and not noCat[prefix .. langCode .. '_rm'] then categories:wikitext('[[Category:',string.upper(langCode),' Romanization Missing]]') end
end
end
--translation section
if Tl and TLcol then
local td = tr:tag('td')
--special format for translations which are non-english loanwords
if (Loanword and Loanword_Tl) then
local CODE = mw.loadData('Module:Lang/code')[Loanword] or nil
if CODE and ne(Loanword_Tl) then td:wikitext(Tl, '<br />(<u>', CODE, '</u>: ', Loanword_Tl, ')')
elseif CODE then td:wikitext('<u>', CODE, '</u>: ', Tl) end
if ie(Tl) and not noCat[prefix .. langCode .. '_tl'] then categories:wikitext('[[Category:',string.upper(langCode),' Translation With Missing Loanword Language]]') end
if ie(Loanword_Tl) and not noCat[prefix .. langCode .. '_lang_tl'] then categories:wikitext('[[Category:',string.upper(langCode),' Loanword With Missing Translation]]') end
--special format for translations which are english loanwords
elseif Loanword then
local CODE = mw.loadData('Module:Lang/code')[Loanword] or nil
if CODE then td:wikitext('<u>', CODE, '</u>: ', Tl) end
if ie(Tl) and not noCat[prefix .. langCode .. '_tl'] then categories:wikitext('[[Category:',string.upper(langCode),' Translation With Missing Loanword Language]]') end
--general [lang]_tl formatting
else
td:wikitext(Tl)
end
if ne(Tl) then
for _, ref in ipairs(Notes) do
if ref.langs[prefix .. langCode] then
td:wikitext( frame:extensionTag{ name = 'ref', content = ref.ref, args = { name = prefix .. ref.langs.name, group = '•' } } )
end
end
if Notes.reuse[prefix .. langCode] then
td:wikitext( frame:extensionTag{ name = 'ref', args = { name = Notes.reuse[prefix .. langCode], group = '•' } } )
end
end
if TLcol == true and ie(Tl) and not noCat[prefix .. langCode .. '_tl'] then
categories:wikitext('[[Category:',string.upper(langCode),' Translation Missing]]')
end
--default behaviour if no [lang]_tl but shown "Literal Meaning" column
elseif TLcol then
--special zh_tl when zhs logic
if (args[prefix .. 'zh_tl'] and search({'zhs','zht'},langCode)) then
if ne(args[prefix .. 'zht']) and langCode == 'zhs' then
local td = tr:tag('td')
td:attr('rowspan',2):wikitext(args[prefix .. 'zh_tl'])
for _, ref in ipairs(Notes) do
if ref.langs[prefix .. 'zh'] then
td:wikitext( frame:extensionTag{ name = 'ref', content = ref.ref, args = { name = prefix .. ref.langs.name, group = '•' } } )
end
end
if Notes.reuse[prefix .. 'zh'] then
td:wikitext( frame:extensionTag{ name = 'ref', args = { name = Notes.reuse[prefix .. 'zh'], group = '•' } } )
end
elseif ne(args[prefix .. 'zhs']) and langCode == 'zht' then
-- do nothing
else
local td = tr:tag('td')
td:wikitext(args[prefix .. 'zh_tl'])
for _, ref in ipairs(Notes) do
if ref.langs[prefix .. 'zh'] then
td:wikitext( frame:extensionTag{ name = 'ref', content = ref.ref, args = { name = prefix .. ref.langs.name, group = '•' } } )
end
end
if Notes.reuse[prefix .. 'zh'] then
td:wikitext( frame:extensionTag{ name = 'ref', args = { name = Notes.reuse[prefix .. 'zh'], group = '•' } } )
end
end
if ie(args[prefix .. 'zh_tl']) and not noCat[prefix .. 'zh_tl'] then categories:wikitext('[[Category:ZH Translation Missing]]') end
--default behaviour if "Literal Meaning" column is shown but no [lang]_tl
else
tr:tag('td'):wikitext('—')
end
end
end
end
--end of loop
end
--check for administrative categories
if (args[prefix .. 'default_hidden'] or args['default_hidden']) and TLcol == true then
categories:wikitext('[[Category:TL Parameters Filled In Despite default_hidden Given]]')
end
if args['hide_tl'] or args['multi'] then
categories:wikitext('[[Category:Pages Using Deprecated Template Parameters]]')
end
if ne(args['revise']) then
categories:wikitext('[[Category:Other Languages Revision Requests]]')
end
--return finished table
return articletable
end
function p.Transclude(retArgs, page, og_index, new_index)
local Parser = require('Module:Parser').getTemplateArgs
local frame = mw.getCurrentFrame()
local og_prefix = ''
local new_index = new_index or og_index or 0
if ne(og_index) then
og_prefix = tostring(og_index) .. '_'
end
local params = Parser(page, {only='Other Languages'})
local at_least_one = false
if params == nil then
categories:wikitext('[[Category:Other Languages Invalid Transclusions]]')
return
end
local new_prefix = tostring(new_index) .. '_'
if new_prefix == '0_' then
new_prefix = ''
end
for param, value in pairs(params) do
local retParam = param
if (tonumber(retParam) ~= nil and tonumber(retParam) == new_index+1)
or (retParam == 'Transclude' and new_index == 0)
or (retParam == ('Transclude_' .. tostring(new_index))) then
error('\n[[Category:Other Languages Invalid Transclusions]]Attempted transclusion of a transcluded table, please utilize the page with the original table [possibly: ' .. value .. ' ]')
elseif retParam:find('^%d_') then
retParam = param:gsub('^%d+_', new_prefix, 1)
elseif new_prefix ~= '' then
retParam = new_prefix .. retParam
end
if retArgs[retParam] == nil and (not param:find('revise')) then
if (og_prefix ~= '' and param:find('^' .. og_prefix)) or (og_prefix == '' and (not param:find('^%d+_'))) then
retArgs[retParam] = frame:preprocess(value)
noCat[retParam] = true
at_least_one = true
end
elseif retArgs[retParam] == '{nil}' then
retArgs[retParam] = nil
end
end
if not at_least_one then
categories:wikitext('[[Category:Other Languages Invalid Transclusions]]')
else
categories:wikitext('[[Category:Other Languages Transcluding Tables]]')
end
end
function p.ParseNotes(args)
-- table concat in sentence format
local function join(tab)
if #tab == 0 then return ''
elseif #tab == 1 then return tab[1]
elseif #tab == 2 then return tab[1] .. ' and ' .. tab[2]
else
local last = table.remove(tab, #tab)
result = table.concat(tab, ', ') .. ', and ' .. last
return result
end
end
local parsedNotes = {}
for param, value in pairs(args) do
if type(param) == 'string' and param:find('_note$') and ne(value) then
param = param:gsub('_note$', '')
local note = { ref = {}, langs = { name = param }, prefix = '' }
local prefix = ''
parsedNotes[param] = true
if param:find('^%d+_') then
prefix, param = string.match(param, '^(%d+_)(.-)$')
note.prefix = prefix
note.langs.name = param
end
-- zhs and zht checks as they're different length
if math.fmod(#param, 2) == 1 and param:find('zht') and not param:find('zhs')then
param = param:gsub('zht', '')
note.langs[note.prefix .. 'zht'] = true
table.insert(note.ref, i18n:msg('zht-ref'))
elseif math.fmod(#param, 2) == 1 and param:find('zhs') and not param:find('zht') then
param = param:gsub('zhs', '')
note.langs[note.prefix .. 'zhs'] = true
table.insert(note.ref, i18n:msg('zhs-ref'))
elseif math.fmod(#param, 2) == 0 and param:find('zht') and param:find('zhs') then
param = param:gsub('zht', ''):gsub('zhs', '')
note.langs[note.prefix .. 'zht'] = true
note.langs[note.prefix .. 'zhs'] = true
table.insert(note.ref, i18n:msg('zhs-ref'))
table.insert(note.ref, i18n:msg('zht-ref'))
end
-- rest of langs
for lang in string.gmatch(param, '%w%w') do
note.langs[note.prefix .. lang] = true
table.insert(note.ref, i18n:msg(lang .. '-ref'))
end
-- build ref content and include in return
note.ref = '<b>' .. join(note.ref) .. ':</b> ' .. value
table.insert(Notes, note)
end
end
for param, value in pairs(args) do
if type(param) == 'string' and param:find('_noteName$') and ne(value) and parsedNotes[value] then
Notes.reuse[param:gsub('_noteName$', '')] = value
end
end
end
function p.CleanTT(tx)
local full = tx
local result = tx
for tooltip, display in string.gmatch(full, '<span[^>]+title="([^>]-)">(.-)</span>') do
search_str = '<span[^>]+title="' .. tooltip .. '">(' .. display .. ')</span><span[^>]+><span[^>]+>' .. display .. '</span><span[^>]+>' .. tooltip .. '</span></span>'
result = result:gsub(search_str, display)
end
return result
end
function p.ruBreak(tx)
local split = {}
local allowed = true
--separate the string through unicode codepoints as default lua split cannot handle non-UTF-8 characters
for c in mw.ustring.gcodepoint(tx) do
table.insert(split, mw.ustring.char(c))
end
-- mw.logObject(split,'split') --debug
--separate the split string into ASCII and non-ASCII, include anything inside '<>' as ASCII to not mess with html tags rendering
local loopnum = 1
local html, ref = 0, false
while split[loopnum] do
--check for start of ref tag
if split[loopnum] == '\'' and split[loopnum+1] == '"' and split[loopnum+2] == '`' then
ref = true
end
--check for start of html
if (split[loopnum] == '<' and split[loopnum+1]:find('%w')) then
html = html + 1
end
if (split[loopnum]:find('%-') and html == 0 and ref == false) then
split[loopnum] = '-<wbr>'
end
--check for end of ref tag
if split[loopnum] == '`' and split[loopnum+1] == '"' and split[loopnum+2] == '\'' then
ref = false
end
--check for end of html
if (split[loopnum] == '|' or (split[loopnum] == ']' and split[loopnum+1] == ']')) then
link = false
end
loopnum = loopnum + 1
end
return table.concat(split, '')
end
return p