Modul:Spisak pjesama
Dokumentaciju za ovaj modul možete napraviti na stranici Modul:Spisak pjesama/dok
--
-- SPISAK PJESAMA
--
local p = {}
local args = {}
local root
-- Bosnian args mapping
local bs_args_map = {
naslov = 'headline',
ukupno_trajanje = 'total_length',
['sakrij_sadržaj'] = 'collapsed',
sve_napisao = 'all_writing',
sva_muzika = 'all_music',
svi_tekstovi = 'all_lyrics',
zasluge_pisanje = 'writing_credits',
zasluge_tekst = 'lyrics_credits',
zasluge_muzika = 'music_credits',
dodatna_kolona = 'extra_column',
naziv = 'title',
['bilješka'] = 'note',
autor = 'writer',
tekst = 'lyrics',
muzika = 'music',
dodatna = 'extra',
trajanje = 'length'
}
local bs_args_value_map = {
['sakrij_sadržaj'] = {da = 'yes'},
zasluge_pisanje = {da = 'yes'},
zasluge_tekst = {da = 'yes'},
zasluge_muzika = {da = 'yes'}
}
local function union(t1, t2, t3)
-- Returns the union of the values of three tables, as a sequence.
local vals = {}
for k, v in pairs(t1) do
vals[v] = true
end
for k, v in pairs(t2) do
vals[v] = true
end
for k, v in pairs(t3) do
vals[v] = true
end
local ret = {}
for k, v in pairs(vals) do
table.insert(ret, k)
end
return ret
end
local function getArgNums(prefix)
-- Returns a table containing the numbers of the arguments that exist
-- for the specified prefix. For example, if the prefix was 'data', and
-- 'data1', 'data2', and 'data5' exist, it would return {1, 2, 5}.
local nums = {}
for k, v in pairs(args) do
local num = tostring(k):match('^' .. prefix .. '([1-9]%d*)$')
if num then table.insert(nums, tonumber(num)) end
end
table.sort(nums)
return nums
end
local function renderHeadline()
if args.headline or args.collapsed == 'yes' then
local headline = root:tag('tr')
local th = headline:tag('th')
:addClass('tlheader')
:addClass('mbox-text')
:attr('colspan', '10')
:css('text-align', 'left')
:css('background-color', '#fff')
if args.headline then
th:wikitext(args.headline)
else
th:wikitext('Spisak pjesama')
end
-- empty
headline:tag('td')
:addClass('mbox-empty-cell')
end
end
local function renderHeader()
local header = root:tag('tr')
:css('background-color', '#eee')
-- index
header:tag('th')
:attr('scope', 'col')
:addClass('tlheader')
:css('width', '2em')
:css('padding-left', '10px')
:css('padding-right', '10px')
:css('text-align', 'right')
:wikitext('Br.')
-- title
local temp = 0
if args.writing_credits == 'yes' then
temp = temp+1
else
if args.lyrics_credits == 'yes' then temp = temp+1 end
if args.music_credits == 'yes' then temp = temp+1 end
end
if args.extra_column then temp = temp+1 end
local title = header:tag('th')
:attr('scope', 'col')
:addClass('tlheader')
:css('text-align', 'left')
:wikitext('Naziv')
if temp == 0 then
title:css('width', '100%')
elseif temp == 1 then
title:css('width', '60%')
elseif temp == 2 then
title:css('width', '40%')
else
title:css('width', '30%')
end
-- writers
if args.writing_credits == 'yes' then
local writers = header:tag('th')
:attr('scope', 'col')
:addClass('tlheader')
:css('text-align', 'left')
:wikitext('Autor(i)')
if args.extra_column then
writers:css('width', '30%')
else
writers:css('width', '40%')
end
else
-- lyrics
if args.lyrics_credits == 'yes' then
local lyrics = header:tag('th')
:attr('scope', 'col')
:addClass('tlheader')
:css('text-align', 'left')
:wikitext('Tekst')
temp = 0
if args.music_credits == 'yes' then temp = temp+1 end
if args.extra_column then temp = temp+1 end
if temp == 0 then
lyrics:css('width', '40%')
elseif temp == 1 then
lyrics:css('width', '30%')
else
lyrics:css('width', '20%')
end
end
-- music
if args.music_credits == 'yes' then
local lyrics = header:tag('th')
:attr('scope', 'col')
:addClass('tlheader')
:css('text-align', 'left')
:wikitext('Muzika')
temp = 0
if args.lyrics_credits == 'yes' then temp = temp+1 end
if args.extra_column then temp = temp+1 end
if temp == 0 then
lyrics:css('width', '40%')
elseif temp == 1 then
lyrics:css('width', '30%')
else
lyrics:css('width', '20%')
end
end
end
-- extra column
if args.extra_column then
local extra = header:tag('th')
:attr('scope', 'col')
:addClass('tlheader')
:css('text-align', 'left')
:wikitext(args.extra_column)
temp = 0
if args.writing_credits then
temp = temp+1
else
if args.lyrics_credits == 'yes' then temp = temp+1 end
if args.music_credits == 'yes' then temp = temp+1 end
end
if temp == 0 then
extra:css('width', '40%')
elseif temp == 1 then
extra:css('width', '30%')
else
extra:css('width', '20%')
end
end
-- length
header:tag('th')
:attr('scope', 'col')
:addClass('tlheader')
:css('width', '4em')
:css('padding-right', '10px')
:css('text-align', 'right')
:wikitext('Trajanje')
-- empty
header:tag('td')
:addClass('mbox-empty-cell')
end
local function addRow(rowArgs)
local row = root:tag('tr')
-- background color
if rowArgs.index % 2 == 0 then
row:css('background-color', '#f7f7f7')
else
row:css('background-color', '#fff')
end
-- index
row:tag('td')
:css('padding-right', '10px')
:css('text-align', 'right')
:css('vertical-align', 'top')
:wikitext(tostring(rowArgs.index))
-- title
local title = row:tag('td')
:css('text-align', 'left')
:css('vertical-align', 'top')
if rowArgs.title then
title:wikitext('"' .. rowArgs.title .. '"')
else
title:wikitext('bez imena')
end
-- note
if rowArgs.note then
title:wikitext(' ')
title:tag('span')
:css('font-size', '85%')
:wikitext('(' .. rowArgs.note .. ')')
end
-- writer
if args.writing_credits == 'yes' then
local writer = row:tag('td')
:css('vertical-align', 'top')
if rowArgs.writer then
writer:wikitext(rowArgs.writer)
end
else
-- lyrics
if args.lyrics_credits == 'yes' then
local lyrics = row:tag('td')
:css('vertical-align', 'top')
if rowArgs.lyrics then
lyrics:wikitext(rowArgs.lyrics)
end
end
--music
if args.music_credits == 'yes' then
local music = row:tag('td')
:css('vertical-align', 'top')
if rowArgs.music then
music:wikitext(rowArgs.music)
end
end
end
-- extra
if args.extra_column then
local extracolumn = row:tag('td')
:css('vertical-align', 'top')
if rowArgs.extra then
extracolumn:wikitext(rowArgs.extra)
end
end
-- length
local length = row:tag('td')
:css('padding-right', '10px')
:css('text-align', 'right')
:css('vertical-align', 'top')
if rowArgs.length then
length:wikitext(rowArgs.length)
end
end
local function renderRows()
-- Get the union of the title, note and length arguments number
local rownums = union(getArgNums('title'), getArgNums('note'), getArgNums('length'))
table.sort(rownums)
local index = 0
for k, num in ipairs(rownums) do
index = index+1
addRow({
index = index,
title = args['title' .. tostring(num)],
note = args['note' .. tostring(num)],
length = args['length' .. tostring(num)],
lyrics = args['lyrics' .. tostring(num)],
music = args['music' .. tostring(num)],
writer = args['writer' .. tostring(num)],
extra = args['extra' .. tostring(num)]
})
end
end
local function renderTotalLength()
if args.total_length then
local row = root:tag('tr')
local colspan = 2;
if args.writing_credits == 'yes' then
colspan = colspan+1
else
if args.lyrics_credits == 'yes' then colspan = colspan+1 end
if args.music_credits == 'yes' then colspan = colspan+1 end
end
if args.extra_column then colspan = colspan+1 end
local td = row:tag('td')
:attr('align', 'right')
:attr('colspan', tostring(colspan))
:css('padding', '0')
td:tag('div')
:css('width', '8.5em')
:css('text-align', 'left')
:css('padding', '5px 0 5px 10px')
:css('background-color', '#eee')
:css('margin', '0')
:tag('b')
:wikitext('Ukupno trajanje:')
row:tag('td')
:css('text-align', 'right')
:css('padding-right', '10px')
:css('background-color', '#eee')
:tag('b')
:wikitext(args.total_length)
-- empty
row:tag('td')
:addClass('mbox-empty-cell')
end
end
local function _track_list()
local html = mw.html.create()
-- text above the table
if args.all_writing then
html:wikitext('Sve pjesme napisao/la i komponovao/la ' .. args.all_writing)
else
if args.all_lyrics then
html:wikitext('Sve tekstove napisao/la ' .. args.all_lyrics)
if args.all_music then html:wikitext(', ') else html:wikitext('. ') end
end
if args.all_music then
if args.all_lyrics then html:wikitext('s') else html:wikitext('S') end
html:wikitext('vu muziku komponovao/la ' .. args.all_music)
end
end
-- (table) root
root = html:tag('table')
root:addClass('tracklist')
if args.collapsed == 'yes' then
root:addClass('mw-collapsible mw-collapsed')
end
root:css('border-spacing', '0px')
root:css('border-collapse', 'collapse')
if args.collapsed == 'yes' then
root:css('border', '#aaa 1px solid')
root:css('padding', '3px')
else
root:css('padding', '4px')
end
renderHeadline()
renderHeader()
renderRows()
renderTotalLength()
return tostring(html)
end
-- Bosnian argument mapping function
local function preprocessBsMapping()
-- Argument value mapping
for k, v in pairs(origArgs) do
if bs_args_value_map[k] then
local mappedValues = bs_args_value_map[k]
if mappedValues[v] then
origArgs[k] = mappedValues[v]
end
end
end
-- Argument name mapping
local new_origArgs = {}
for k, v in pairs(origArgs) do
local prefix, num = tostring(k):match('^(%D+)(%d*)$')
if (bs_args_map[prefix] and origArgs[k]) then
postfix = ''
if num then
postfix = num
end
new_key = bs_args_map[prefix] .. postfix
new_origArgs[new_key] = origArgs[k]
end
end
origArgs = new_origArgs
end
local function preprocessSingleArg(argName)
-- If the argument exists and isn't blank, add it to the argument table.
-- Blank arguments are treated as nil to match the behaviour of ParserFunctions.
if (origArgs[argName] and origArgs[argName] ~= '') then
args[argName] = origArgs[argName]
end
end
local function preprocessArgs(prefixTable, step)
-- Assign the parameters with the given prefixes to the args table, in order, in batches
-- of the step size specified. This is to prevent references etc. from appearing in the
-- wrong order. The prefixTable should be an array containing tables, each of which has
-- two possible fields, a "prefix" string and a "depend" table. The function always parses
-- parameters containing the "prefix" string, but only parses parameters in the "depend"
-- table if the prefix parameter is present and non-blank.
if type(prefixTable) ~= 'table' then
error("Non-table value detected for the prefix table", 2)
end
if type(step) ~= 'number' then
error("Invalid step value detected", 2)
end
-- Get arguments without a number suffix, and check for bad input.
for i,v in ipairs(prefixTable) do
if type(v) ~= 'table' or type(v.prefix) ~= "string" or (v.depend and type(v.depend) ~= 'table') then
error('Invalid input detected to preprocessArgs prefix table', 2)
end
preprocessSingleArg(v.prefix)
-- Only parse the depend parameter if the prefix parameter is present and not blank.
if args[v.prefix] and v.depend then
for j, dependValue in ipairs(v.depend) do
if type(dependValue) ~= 'string' then
error('Invalid "depend" parameter value detected in preprocessArgs')
end
preprocessSingleArg(dependValue)
end
end
end
-- Get arguments with number suffixes.
local a = 1 -- Counter variable.
local moreArgumentsExist = true
while moreArgumentsExist == true do
moreArgumentsExist = false
for i = a, a + step - 1 do
for j,v in ipairs(prefixTable) do
local prefixArgName = v.prefix .. tostring(i)
if origArgs[prefixArgName] then
moreArgumentsExist = true -- Do another loop if any arguments are found, even blank ones.
preprocessSingleArg(prefixArgName)
end
-- Process the depend table if the prefix argument is present and not blank, or
-- we are processing "prefix1" and "prefix" is present and not blank, and
-- if the depend table is present.
if v.depend and (args[prefixArgName] or (i == 1 and args[v.prefix])) then
for j,dependValue in ipairs(v.depend) do
local dependArgName = dependValue .. tostring(i)
preprocessSingleArg(dependArgName)
end
end
end
end
a = a + step
end
end
function p.track_list(frame)
-- If called via #invoke, use the args passed into the invoking template.
-- Otherwise, for testing purposes, assume args are being passed directly in.
if frame == mw.getCurrentFrame() then
origArgs = frame:getParent().args
else
origArgs = frame
end
preprocessBsMapping()
preprocessSingleArg('all_writing')
preprocessSingleArg('all_lyrics')
preprocessSingleArg('all_music')
preprocessSingleArg('collapsed')
preprocessSingleArg('headline')
preprocessSingleArg('writing_credits')
preprocessSingleArg('lyrics_credits')
preprocessSingleArg('music_credits')
preprocessSingleArg('extra_column')
preprocessArgs({
{prefix = 'title'},
{prefix = 'note'},
{prefix = 'length'},
{prefix = 'lyrics'},
{prefix = 'music'},
{prefix = 'writer'},
{prefix = 'extra'}
}, 120)
preprocessSingleArg('total_length')
return _track_list()
end
return p