Dead by Daylight Wiki

Nuovo Contenuto in Arrivo: Volume IX - Crescendo - 20 Ottobre
Con Yun-Jin Lee SurvivorYun-Jin.png e L'Ingannatore IconHelpLoading trickster.png
Metà Capitolo 21.5 - 19 Ottobre 2021
Evento di Halloween The Midnight Grove - 21 Ottobre 2021

LEGGI DI PIÙ

Dead by Daylight Wiki
Advertisement
Dead by Daylight Wiki

La documentazione per questo modulo può essere creata in Modulo:Utils/man

local p = {}
local mathOps = require("Modulo:MathOps")
local str = require("Modulo:Strings")
local frame = mw.getCurrentFrame()
local _brigtnessTreshold = 0.36

local strings = {
	male = "Maschile",
	female = "Femminile",
	nonhuman = "Non Applicabile (non umano)";
	undefined = "Non Definito",
	charNotFound = "Personaggio Non Trovato!",
}

p.strings = strings

function p.resolveParameter(param, index, returnPageTitle)
	local retArg
	if type(param) == "table" then retArg = (param.args and param.args[(index or 1)]) end --if parameter is passed from wiki, not other function
	if retArg == nil and not returnPageTitle then retArg = (param or mw.title.getCurrentTitle().text) end --if parameter was passed directly or not at all
	if retArg ~= nil and type(param) ~= "table" then retArg = p.replaceSpecialCharacters(retArg) end --final processing
	return retArg
end

function p.getCount(subject)
	local list
	subject = p.resolveParameter(subject)
	--if you have another list just add it into a list then call appropriate function
	if		subject == "map"		then list = maps
	elseif	subject == "realm"		then list = realms
	elseif	subject == "killer"		then list = killers
	elseif	subject == "survivor"	then list = survivors
	elseif	subject == "dlc"		then list = dlcs
	elseif	subject == "chapter"	then return getCountDlcType(1)
	elseif	subject == "paragraph"	then return getCountDlcType(2)
	elseif	subject == "clothing"	then return getCountDlcType(3)
	elseif	subject == "ost"		then return getCountDlcType(4)
	elseif	subject == "character"	then return getCountDlcType(5)
	elseif	subject == "ccy"		then return getCountCCY(true)
	elseif	subject == "ccy-gc"		then return getCountCCY(true) --redundant option to keep convention
	elseif	subject == "ccy-rc"		then return getCountCCY(false)
	elseif	subject == "killerPerk"	then return getPerksCount('K')
	elseif	subject == "survPerk"	then return getPerksCount('S')
	else return 0
	end
	
	local x = 0
	for _, item in ipairs(list) do if item.skip then x = x + 1 end end
	
	return #list - x
end

function getCountDlcType(type)
	local count = 0
	
	for _, dlc in ipairs(dlcs) do
		if dlc.category == type and not dlc.skip then count = count + 1 end
	end
	
	return count
end

function getPerksCount(charType)
	require("Modulo:Datatable/Perks")
	local count = 0
	
	for _, perk in ipairs(perks) do
		if perk.charType == charType and not perk.unused then count = count + 1 end
	end

	return count
end

function getCountCCY(gc)
	local list = ccy

	local i = 0
	while list[i + 1] and list[i + 1].gc == gc do i = i + 1 end

	return i
end

-- Function allowing for consistent treatment of boolean-like wikitext input.
-- It works similarly to the template {{yesno}}.

function p.bool(val, default)
	-- If your wiki uses non-ascii characters for any of "yes", "no", etc., you
	-- should replace "val:lower()" with "mw.ustring.lower(val)" in the
	-- following line.
	val = type(val) == 'string' and val:lower() or val
	if val == nil then
		return nil
	elseif val == true 
		or val == 'yes'
		or val == 'y'
		or val == 'true'
		or val == 't'
		or val == 'on'
		or tonumber(val) == 1
	then
		return true
	elseif val == false
		or val == 'no'
		or val == 'n'
		or val == 'false'
		or val == 'f'
		or val == 'off'
		or tonumber(val) == 0
	then
		return false
	else
		return default
	end
end

function p.split (inputstr, sep)
        if sep == nil then
            sep = "%s"
        end
        local t = {}
        for str in string.gmatch(inputstr, "([^"..sep.."]+)") do
            table.insert(t, str)
        end
        return t
end

--Example usage:
--amount = 1333444.1
--print(format_num(amount,2))
--print(format_num(amount,-2,"US$"))
--amount = -22333444.5634
--print(format_num(amount,2,"$"))
--print(format_num(amount,2,"$","()"))
--print(format_num(amount,3,"$","NEG "))

--Output:
--1,333,444.10
--US$1,333,400
---$22,333,444.56
--($22,333,444.56)
--NEG $22,333,444.563

function p.format_num(amount, decimal, prefix, neg_prefix)
  local str_amount,  formatted, famount, remain

  decimal = decimal or 2  -- default 2 decimal places
  neg_prefix = neg_prefix or "-" -- default negative sign

  famount = math.abs(mathOps.round(amount,decimal))
  famount = math.floor(famount)

  remain = mathOps.round(math.abs(amount) - famount, decimal)

        -- comma to separate the thousands
  formatted = p.commaFormat(famount)

        -- attach the decimal portion
  if (decimal > 0) then
    remain = string.sub(tostring(remain),3)
    formatted = formatted .. "." .. remain ..
                string.rep("0", decimal - string.len(remain))
  end

        -- attach prefix string e.g '$' 
  formatted = (prefix or "") .. formatted 

        -- if value is negative then format accordingly
  if (amount<0) then
    if (neg_prefix=="()") then
      formatted = "("..formatted ..")"
    else
      formatted = neg_prefix .. formatted 
    end
  end

  return formatted
end

function p.commaFormat(amount)
  local formatted = amount
  while true do  
    formatted, k = string.gsub(formatted, "^(-?%d+)(%d%d%d)", '%1,%2')
    if (k==0) then
      break
    end
  end
  return formatted
end

--Converting Arabic numbers to Roman
function ToRomanNumerals(s)
    local numbers = { 1, 5, 10, 50, 100, 500, 1000 }
	local chars = { "I", "V", "X", "L", "C", "D", "M" }

    s = tonumber(s)
    if not s or s ~= s then error"Unable to convert to number" end
    if s == math.huge then error"Unable to convert infinity" end
    s = math.floor(s)
    if s <= 0 then return s end
	local ret = ""
        for i = #numbers, 1, -1 do
        local num = numbers[i]
        while s - num >= 0 and s > 0 do
            ret = ret .. chars[i]
            s = s - num
        end
        for j = 1, i - 1 do
            local n2 = numbers[j]
            if s - (num - n2) >= 0 and s < num and s > 0 and num - n2 ~= n2 then
                ret = ret .. chars[j] .. chars[i]
                s = s - (num - n2)
                break
            end
        end
    end
    return ret
end

--Converting Roman numbers to Arabic
function ToNumeral(roman)
    local Num = { ["M"] = 1000, ["D"] = 500, ["C"] = 100, ["L"] = 50, ["X"] = 10, ["V"] = 5, ["I"] = 1 }
    local numeral = 0    
 
    local i = 1
    local strlen = string.len(roman)
    while i < strlen do
        local z1, z2 = Num[ string.sub(roman,i,i) ], Num[ string.sub(roman,i+1,i+1) ]
        if z1 < z2 then
            numeral = numeral + ( z2 - z1 )
            i = i + 2
        else
            numeral = numeral + z1
            i = i + 1    
        end        
    end
 
    if i <= strlen then numeral = numeral + Num[ string.sub(roman,i,i) ] end
 
    return numeral    
end

function resolveNameWithRomanNumbers(str)
	local index = string.find(str, " [^ ]*$") + 1
	local romanNumber = (string.sub(str, index))
	local result
	if string.match(romanNumber, "[MDCLXVI]+$") then --finding ONLY Roman letters in last "word"
		--Cowshed
		mw.log(romanNumber)
		result = str
		--result = string.sub(str, 1, index - 1) .. ToNumeral(romanNumber)
	else
		mw.log("Non-Roman form")
		result = str
	end
	
	return result
end

function p.CapitalizeName(str)
	return string.gsub(" "..str, "%W%l", string.upper):sub(2)
end

function p.FirstLetterLower(str)
	return str:sub(1, 1):lower() .. str:sub(2)
end

--[[function p.fixDiacritics(str)
	local letterSequences = {
		["195"] = {fix = "â", sequence = {"162"}}
	}
	local fixedSeqsOffset = 0

	local currentLen = #str + fixedSeqsOffset
	local i = 1
	while i <= currentLen do
		local ascii = tostring(string.byte(str:sub(i,i)) or 0)
		for startSequence, seqData in pairs(letterSequences) do
			if ascii == startSequence then
				local foundSequence = true
				for j, seqCode in ipairs(seqData.sequence) do
					local seqAscii = tostring(string.byte(str:sub(i+j,i+j)))
					if seqAscii ~= seqCode then
						foundSequence = false
						break
					end
				end
				
				if foundSequence then
					fixedSeqsOffset = i - (i + #seqData.sequence)
					currentLen = #str + fixedSeqsOffset
					-- #seqData.sequence + 1 = number of ascii codes that needs to be replaced, the sequence list + the initial ascii code, i.e. the key value from letterSequences
					str = str:sub(1, i - 1) .. seqData.fix .. str:sub(i + #seqData.sequence + 1)
				end
			end
		end
		i = i + 1
	end
	return str
end]]

function p.RemoveSpecialCharacters(str, full, replaceDiacritics)
	str = string.gsub(str, "'", "")
	str = string.gsub(str, "®", "")
	str = string.gsub(str, "™", "")
	str = string.gsub(str, ":", "")
	str = string.gsub(str, "!", "") --perks
	str = string.gsub(str, "&", "And") --probably can be changed to lower: "and"

	if replaceDiacritics then
		str = p.replaceDiacritics(str, full)
	end
		
	return str
end

function p.replaceDiacritics(str, full)
	--Diacritics
	specialLettersLight = {
		["A"] = {"À", "Á", "Â", "Ã", "Ä"},
		["a"] = {"à", "á", "â", "ã", "ä"},
		["e"] = {"è", "é", "ê", "ë", "ě"},
		["O"] = {"Ò", "Ó", "Ô", "Õ", "Ö"},
		["o"] = {"ò", "ó", "ô", "õ", "ö"}
	}
	specialLetters = {
		["A"] = {"À", "Á", "Â", "Ã", "Ä"},
		["a"] = {"à", "á", "â", "ã", "ä"},
		["E"] = {"È", "É", "Ê", "Ë", "Ě"},
		["e"] = {"è", "é", "ê", "ë", "ě"},
		["I"] = {"Ì", "Í", "Î", "Ñ", "Ï"},
		["i"] = {"ì", "í", "î", "ñ", "ï"},
		["O"] = {"Ò", "Ó", "Ô", "Õ", "Ö"},
		["o"] = {"ò", "ó", "ô", "õ", "ö"},
		["U"] = {"Ù", "Ú", "Û", "Ů", "Ü"},
		["u"] = {"ù", "ú", "û", "ů", "ü"},
		["Y"] = {	  "Ý",			 "Ÿ"},
		["y"] = {	  "ý",			 "ÿ"}
	}
	--Originally it was grouped by set [ÀÁ], however there is some sort of bug there that makes it not working
	--str = string.gsub(str, "[ÁÂ]", "A")
	--if debugRun then mw.log(mw.dumpObject(specialLetters)) end
	for letter, row in pairs(((full and specialLetters) or specialLettersLight)) do
		for _, special in ipairs(row) do
			str = str:gsub(special, letter)
		end
	end
	return str
end

function p.replaceSpecialCharacters(name)
	local charList = { 
		["'"] = '&#39;',
		["&"] = '&#38;'
	}
	if name == nil then error("Name parameter is empty, but it shouldnt?") end
	for repl, sChar in pairs(charList) do
		name = string.gsub(name, sChar, repl)
	end
	return name
end

function p.isValidFileName(name, extension)
	extension = extension or "png"
	name = p.RemoveSpecialCharacters(name)
	return not (name == "" or not mw.title.new("File:" .. name .. "." .. extension).exists)
end

function p.resolveFileName(str, keepSpaces, removeDiacritics)
	keepSpaces = keepSpaces or false
	local result = ""
	
	result = string.lower(str)
	--mw.log(result)
	result = p.RemoveSpecialCharacters(result, keepSpaces, removeDiacritics)
	--mw.log(result)
	result = p.CapitalizeName(result)
	if not keepSpaces then
		result = string.gsub(result, "[ ]", "")
	end
	--In future if there will be needed replace charactere such as "é" just add another substitution
	
	--mw.log(result)
	return result
end
	
function p.resolveImageName(name)
	if mw.title.new("File:" .. name .. ".png").exists then return name .. ".png" end
	if mw.title.new("File:" .. name .. ".jpg").exists then return name .. ".jpg" end
	return name .. ".png"
end

function p.GetDisplayName(item)
	return (item.tName or item.name)
end

function p.clr(text, color)
	return frame:expandTemplate{title = "clr", args = {color, text}}	
end

function p.IconLink(name, pageLink, displayText)
	return frame:expandTemplate{title = "IconLink", args = {name, pageLink, displayText} }	
end

function p.resolveTextColorByBackground(hexBgColor)
	if(type(hexBgColor) == "table") then
		hexBgColor = hexBgColor.args[1]
	end
	local red = tonumber(string.sub(hexBgColor, 1, 2), 16)
	local green = tonumber(string.sub(hexBgColor, 3, 4), 16)
	local blue = tonumber(string.sub(hexBgColor, 3, 4), 16)
	local darkness = (0.299 * red + 0.587 * green + 0.114 * blue) / 255
	
	mw.log("Red: " .. red .." | Blue: " .. blue .. " | Green: " .. green)
	mw.log(darkness)
	if(darkness < _brigtnessTreshold) then
		return "white"
	else
		return "black"
	end
end

function p.getPageTitle()
	return mw.title.getCurrentTitle().text
end
---------------------------------------------------------------------------------
function p.getSumOfASTiles(row)
	local result = 0
	local i = 1
	while row[i] do
		result = result + row[i][1] -- hardcoded first variable in table
		i = i + 1
	end
	return result
end

function compASTiles(row1, row2)
	local sum1 = row1.ASTiles
	local sum2 = row2.ASTiles
	if(type(sum1) == "table") then
		sum1 = p.getSumOfASTiles(sum1) --converting back from table to number
	end
	if(type(sum2) == "table") then
		sum2 = p.getSumOfASTiles(sum2)
	end
	
	if sum1 > sum2 then return true
	elseif sum1 < sum2 then return false
	else 
		if row1.realm < row2.realm then return true
		elseif row1.realm > row2.realm then return false
		else
			return resolveNameWithRomanNumbers(row1.name) < resolveNameWithRomanNumbers(row2.name)
		end
	end
end

function compMapRateSize(row1, row2)
	return row1.size > row2.size --comparison specificly made for mapRates table
end

function compName(row1, row2)
	if row1.diacritics then
		if row2.diacritics then
			return p.RemoveSpecialCharacters(row1.name, true) < p.RemoveSpecialCharacters(row2.name, true)
		else
			return p.RemoveSpecialCharacters(row1.name, true) < row2.name
		end
	elseif row2.diacritics then
		return row1.name < p.RemoveSpecialCharacters(row2.name, true)
	end
	return row1.name < row2.name
end

function compInt(row1, row2)
	return row1 < row2
end

function compLevel(row1, row2)
	return row1.level < row2.level
end

function compDlcCategory(row1, row2)
	if row1.category == row2.category then
		return row1.id < row2.id
	end
	return row1.category < row2.category
end

function compId(row1, row2)
	return row1.id < row2.id
end

function p.sortMapsByASTiles()
	local m = require("Modulo:Datatable")
	--mw.log(mw.dumpObject(maps))
	table.sort(maps,compASTiles)
	--mw.log(mw.dumpObject(maps))
end

function p.sortMapRates(rankTable)
	--mw.log(mw.dumpObject(rankTable))
	table.sort(rankTable, compMapRateSize)
	--mw.log(mw.dumpObject(rankTable))
end

function p.sortItemsByName(tableList)
	table.sort(tableList, compName)
end

function p.sortTable(tableList)
	table.sort(tableList, compInt)
end

function p.sortDlcByCategory(tableList)
	table.sort(tableList, compDlcCategory)
end

function p.sortPerksByLevel(tableList)
	table.sort(tableList, compLevel)	
end

function p.sortTableById(tableList)
	table.sort(tableList, compId)
end

---------------------------------------------------------------------------------

function p.getCountOfSoundtracks()
	return utils.getCount("ost")
end

function p.resolveDateTime(datetime) --with weekday
	matchYear = "^(##)%.(##)%.(%d%d%d%d)$"
	matchMonth = "^(##)%.(%d%d)%.(%d%d%d%d)$"
	local rDate = os.time(p.GetDatetime(datetime))
	if string.find(datetime, matchYear) then
		return os.date("%Y", rDate)
	elseif string.find(datetime, matchMonth) then
		return os.date("%B %Y", rDate)
	end
	return os.date("%d %B %Y (%A)", rDate)
end

function p.IsFullDateTime(datestamp)
	local day, month, year = datestamp:match("^(..)%.(..)%.(....)$")
	if month == "##" or day == "##" or year == "####" then return false end
	return true
end

function p.GetDatetime(datestamp)
	local day, month, year = datestamp:match("^(..)%.(..)%.(%d%d%d%d)$")
	if month == "##" then month = 1 end
	if day == "##" then day = 1 end
	return {year = year, month = month, day = day}
end

function p.regularReplace(reggedString, regexTable)
	local result = ""
	local regexString = regex --"#pl%((%d)%)" -- looking and extracting number from "#pl(x)"
	for key, value in pairs(regexTable) do
		reggedString = reggedString:gsub(key, value)
	end
	--for m in reggedString:gmatch(regex) do
	--	mw.log(mw.dumpObject(m))
	--	result = reggedString:gsub(regexString, "string")
	--	mw.log(result)
	--end
	return reggedString
end

function p.getIcon(icon)
	icon = p.resolveParameter(icon)
	require("Modulo:Datatable/Icons")
	
	for _, element in ipairs(icons) do
		if icon == element.icon then
			return element.iconFile
		end
	end
	return icons[1].iconFile --Icon not found, then pick the first one which is supposed to be the Unknown one
end

function p.getIconTest(icon)
	local iconR = ""
	if type(icon) == "table" then
		icon = icon.args[1] or mw.title.getCurrentTitle().text
	end
	require("Modulo:Datatable/Icons")
	
	for _, element in ipairs(icons) do
		iconR = iconR .. "icon [" .. icon .. "] == [" .. element.icon .. "] element.icon<br>"
		if icon == element.icon then
			iconR = iconR .. "TROVATO"
			return iconR
		end
	end
	iconR = iconR .. "NON TROVATO"
	return iconR
end

--************************* survivors & killers ******************************--

function p.getCharacterById(id, charTable)
	for _, character in ipairs(charTable) do
		if character.id == id then return character end
	end
	return strings.charNotFound
end

function p.resolveGender(abbr)
	if		abbr == 'M'		then return strings.male
	elseif	abbr == 'F'		then return strings.female
	elseif  abbr == 'N'		then return strings.nonhuman
	else						 return strings.undefined
	end
end

function p.wrapBasicTable(content)
	return '{| class = "wikitable sortable"' .. nl .. ntl .. nl .. content ..'|}'
end

return p
Advertisement