Module:D'ni Tools

From Guild of Archivists
Revision as of 23:55, 20 September 2020 by BladeLakem (talk | contribs)
(diff) ← Older revision | Latest revision (diff) | Newer revision → (diff)
The printable version is no longer supported and may have rendering errors. Please update your browser bookmarks and please use the default browser print function instead.

Documentation for this module may be created at Module:D'ni Tools/doc

--
-- This implements several useful functions for dealing with D'ni text in the Wiki.
--
-- parsed_dni() returns a string in which every component is linked to its appropriate Dictionary namespace entry.
-- dnifont2ots() converts a Dnifont string to an ots one
-- dnifont2nts() converts a Dnifont string to an nts one

local p = {}

local args = {}
local origArgs
local root

local output = ''

-- Local Functions

local function num2dnum(str,sep)
        str = str or ''

	str = mw.text.trim(str)
	
	if (sep == nil or sep == '') then
		sep = "|"
	end
	
	local output = "nil"
	local num = tonumber(str)
	
	if (num ~= nil and num >= 0) then
		output = num % 25
		while (num >= 25) do
			num = math.floor(num / 25)
			output = tostring(num % 25)..sep..output
		end
	end 
	
	return output
	
end

local function dnum2num(str,sep)
	
	  str = str or ''
	  sep = sep or ''
	
	  local output = mw.text.trim(str)
	
	  output = mw.ustring.gsub(output,"%d%d",  {["24"] = "O", 
                                 ["23"] = "N", 
                                 ["22"] = "M", 
                                 ["21"] = "L", 
                                 ["20"] = "K", 
                                 ["19"] = "J", 
                                 ["18"] = "I", 
                                 ["17"] = "H",
                                 ["16"] = "G",
                                 ["15"] = "F",
                                 ["14"] = "E",
                                 ["13"] = "D",
                                 ["12"] = "C",
                                 ["11"] = "B",
                                 ["10"] = "A"
                                })
                                
    output = mw.ustring.gsub(output,sep,"") 
    
    output = tonumber(output,25)
    
    return output
                              
end

local function dnum2dnifont(str,min,use25,useWrap)

    str = str or ""
    min = min or 0
    use25 = use25 or false
    useWarp = useWrap or false

    local output = mw.text.trim(str)
    
    if str == "25" and use25 then output = "|"
    elseif str == "0" and useWrap then output = "="
    else 
       output = mw.ustring.gsub(output,"%d%d",  {["24"] = "}", 
                                 ["23"] = "{", 
                                 ["22"] = "\\", 
                                 ["21"] = "]", 
                                 ["20"] = "[", 
                                 ["19"] = "(", 
                                 ["18"] = "*", 
                                 ["17"] = "&",
                                 ["16"] = "^",
                                 ["15"] = "%",
                                 ["14"] = "$",
                                 ["13"] = "#",
                                 ["12"] = "@",
                                 ["11"] = "!",
                                 ["10"] = ")"
                                })

       output = mw.ustring.gsub(output,"%|","")
       if #output < min then output = string.rep("0", (min - #output))..output end
    end

    return output
	
	
end

local function dnifont2dnum(str,sep)

    str = mw.text.trim(str)
    
    local chars = mw.text.split(str,'')
    
    local output = table.concat(chars,sep)
    
    
    output = mw.ustring.gsub(output,"%S",  {["}"] = "24" , 
                                 ["{"] = "23", 
                                 ["\\"] = "22", 
                                 ["]"] = "21", 
                                 ["["] = "20", 
                                 ["("] = "19", 
                                 ["*"] = "18", 
                                 ["&"] = "17",
                                 ["^"] = "16",
                                 ["%"] = "15",
                                 ["$"] = "14",
                                 ["#"] = "13",
                                 ["@"] = "12",
                                 ["!"] = "11",
                                 [")"] = "10"
                                })

    return output
	
end

local function dnifont2ots(str)

    local output = mw.text.trim(str)
    
    output = mw.ustring.gsub(str,"%S",  {["S"] = "sh", 
                                 ["T"] = "th", 
                                 ["O"] = "oy", 
                                 ["c"] = "ch", 
                                 ["a"] = "ah", 
                                 ["E"] = "ee", 
                                 ["A"] = "ay", 
                                 ["u"] = "uh",
                                 ["U"] = "oo",
                                 ["x"] = "ts",
                                 ["d"] = "dh",
                                 ["D"] = "d",
                                 ["k"] = "kh",
                                 ["K"] = "k",
                                 ["I"] = "ai",
                                 ["å"] = "a",
                                })

     return output
end
 
local function dnifont2nts(str)

    local output = mw.text.trim(str)
    
    output = mw.ustring.gsub(str,"%S",  {["S"] = "š", 
                                 ["T"] = "þ", 
                                 ["O"] = "ó", 
                                 ["c"] = "ç", 
                                 ["E"] = "í", 
                                 ["A"] = "é", 
                                 ["U"] = "ú",
                                 ["x"] = "c",
                                 ["d"] = "ð",
                                 ["D"] = "d",
                                 ["k"] = "x",
                                 ["K"] = "k",
                                 ["I"] = "á",
                                 ["å"] = "æ",
                                })

     return output
end



local function parseDniWord(input,count)

    local output 

    local name = 'quote'..count

    local word = mw.text.trim(input)
    local first = mw.ustring.sub(word,1,1)
    local last = mw.ustring.sub(word,-1,-1)
    local prefix = ''
    local suffix = ''

    if (word == mw.ustring.lower(mw.title.getCurrentTitle().rootText)) then
         prefix = '\'\'\''
         suffix = prefix
    end 


    if (word == '') then
        output = ' '
    elseif (word == '&nbsp;') then
        output = '&nbsp;'
    elseif (word == '.' or word == '?' or word == '!' or word == ',') then
        output = first
    elseif (first == '-') then
        output = prefix..'[[Dictionary:'..word..'|'..mw.ustring.sub(word,2,-1)..']]'..suffix
        mw.smw.subobject('ContainsTerm=Dictionary:'..word,name)
    elseif (last == '-') then
        output = prefix..'[[Dictionary:'..word..'|'..mw.ustring.sub(word,1,-2)..']]'..suffix
        mw.smw.subobject('ContainsTerm=Dictionary:'..word,name)
    elseif (first == '.' or first == '!' or first == '?' or first == ',') then
        output = first..prefix..'[[Dictionary:'..mw.ustring.sub(word,2,-1)..'|'..mw.ustring.sub(word,2,-1)..']]'..suffix
        mw.smw.subobject('ContainsTerm=Dictionary:'..mw.ustring.sub(word,1,-2),name)
    elseif (last == ',') then
        output = prefix..'[[Dictionary:'..mw.ustring.sub(word,1,-2)..'|'..mw.ustring.sub(word,1,-2)..']]'..suffix..last
        mw.smw.subobject('ContainsTerm=Dictionary:'..mw.ustring.sub(word,1,-2),name)
    else
        output = prefix..'[[Dictionary:'..word..'|'..word..']]'..suffix
        mw.smw.subobject('ContainsTerm=Dictionary:'..word,name)
    end


    return output
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

function p.parsed_dni(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.args
    end

    count=0
    if (frame:callParserFunction('#varexists:count') ~= '1') then
        frame:callParserFunction('#vardefine:count','0')
    else
        count = tonumber(frame:callParserFunction('#var:count'))
        count = count + 1
        frame:callParserFunction('#vardefine:count',count)
    end

    for word in ipairs(origArgs) do
        output = output..parseDniWord(origArgs[word],count)
    end
    name='quote'..count
    quote=string.gsub(output,'%|','{{!}}')
--    quote=mw.text.nowiki(output)
    mw.smw.subobject('ContainsQuote='..quote,name)

    return output
end

-- For call by other Modules
function p._num2dnum(str,sep)
   return num2dnum(str,sep)
end

function p._dnum2num(str,sep)
   return dnum2num(str,sep)
end

function p._dnum2dnifont(str,min,use25,useWrap)
   return dnum2dnifont(str,min,use25,useWrap)
end

function p._dnifont2dnum(str,sep)
   return dnifont2dnum(str,sep)
end

function p._num2dnifont(str,min,use25,useWrap)
   return dnum2dnifont(num2dnum(str),min,use25,useWrap)

end

function p.dnifont2ots(frame)

    return dnifont2ots(frame.args[1])
end

function p.dnifont2nts(frame)

    return dnifont2nts(frame.args[1])
end

function p.num2dnum(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.args
    end

    preprocessSingleArg(1)
    preprocessSingleArg('val')
    preprocessSingleArg('format')
    preprocessSingleArg('sep')

    local output 
	

    local val = args['val'] or args[1]
	
	if (args['format'] == 'dnifont') then
		output = dnum2dnifont(num2dnum(val))
	else
		output = num2dnum(val,args['sep'])
		
	end
	
    return output
end

function p.dnifont2dnum(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.args
    end

    preprocessSingleArg(1)
    preprocessSingleArg('sep')

	return dnifont2dnum(args[1],args['sep'])
end

function p.dnum2num(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.args
    end

    preprocessSingleArg(1)
    preprocessSingleArg('sep')

	return dnum2num(args[1],args['sep'])
end

return p