Module:Array

From Coral Island Wiki
Jump to navigation Jump to search

Documentation for this module may be created at Module:Array/doc

--- Module copied from Genshin Impact wiki

local p = {}
local lib = require('Module:Feature')

function p.main(frame)
	local args = require('Module:Arguments').getArgs(frame, {
		parentFirst = true,
		wrapper = { 'Template:Array' }
	})
	--mw.logObject(args,'args') --debug
	return p._main(args, frame)
end

function p._main(args, frame)
	local arrayString = args[1] or nil
	local separator = args[2] or nil
	local format = args[3] or nil
	local join = args[4] or ''
	local dedupe = args['dedupe'] or nil
	local sort = args['sort'] or nil
	local sentence = args['sentence'] or nil
	local template = args['template'] or nil
	local prefix = args['prefix'] or ''
	local suffix = args['suffix'] or ''

	-- argument validation
	if arrayString == nil then return '' end
	if separator == nil then return error('Second argument (separator) must not be empty.') end
	if separator == '' then return error('Second argument (separator) must not be empty string.') end
	if format == nil then return error('Third argument (format) must not be empty.') end
	if format:find('{item}') == nil then return error('Third argument (format) does not include {item}.') end

	-- split string to array
	local array = lib.split(arrayString, separator)

	-- remove duplcates from array
	if dedupe == '1' then
		array = p._removeDuplicates(array)
	end
	
	-- sort array
	if sort ~= nil then
		array = p._sort(array, sort)
	end
	
	-- replace keywords in array
	for key, value in pairs(array) do
		local item = format
		item = item:gsub('{item}', value)
		item = item:gsub('{newline}', '\n')
		item = item:gsub('{index}', key)
		array[key] = item
	end
	
	-- mw.logObject(array)
	
	-- create result array
	local result = ''
	
	-- join as sentence
	if sentence ~= nil then
		if #array == 0 then return ''
		elseif #array == 1 then return array[1]
		elseif #array == 2 then return array[1] .. ' and ' .. array[2]
		else
			local last = table.remove(array, #array)
			result = table.concat(array, ', ') .. ', and ' .. last
		end
	-- join with join string
	else
		result = table.concat(array, join):gsub('{newline}', '\n')--in case joining string contains keyword
	end
	result = prefix .. result .. suffix
	if template then
		result = result:gsub('²{(.-)}²','{{%1}}'):gsub('¦','|')
		result = frame:preprocess(result)
	end
	return result
end

function p._removeDuplicates(arr)
	local hash = {}
	local res = {}

	for _,v in ipairs(arr) do
	   if (not hash[v]) then
	       res[#res+1] = v
	       hash[v] = true
	   end
	end

	return res
end

function p._sort(arr, dir)
	local order = nil
	if (dir == -1 or dir == '-1') then
		order = function(tVal, a, b) return a > b end
	elseif (dir == 1 or dir == '1') then
		order = function(tVal, a, b) return a < b end
	else
		return arr
	end
	table.sort(arr, function(a, b) return order(t, a, b) end)
	return arr
end

return p