Moduuli:ParametrisoituTeksti
Moduulin ParametrisoituTeksti käyttöohje [näytä tämä käyttöohje omalla sivullaan] [muokkaa tätä käyttöohjetta] [päivitä] [testit] [hiekkalaatikko]
Tässä ohjeessa kuvataan toiminnallisuutta jonka kehitys on vielä kesken. Sivu on tarkoitettu lähinnä kehityksen apuvälineeksi, ei yleiseen käyttöön. |
Kirjaston avulla voi tehdä helposti tekstejä, joissa ehdollisia kohtia. Kirjaston avulla voi varmistaa, että lopputulos on järkevä rippumatta siitä mikä yhdistelmä parametreja on annettu.
Moduulin funktiot
[muokkaa]muotoile
[muokkaa]muotoile(rakenne)
Pääfunktio, joka prosessoi annetun elementtirakenteen ja palauttaa sen tuottaman tekstin. Tämä on lyhyt tapa tehdä peräkkäin uusi_muotoilija, prosessoi ja tostring(muotoilija)
uusi_muotoilija
[muokkaa]uusi_muotoilija()
Luo uuden muotoiluolion. Tätä ei tarvitse kutsua suoraan, jos käytetään muotoile-funktiota.
Rakenne-elementit
[muokkaa]Tekstin rakenne kuvataan alla luetelluilla elementeillä. Kun elementti evaluoidaan, se voi tuottaa pätkän tekstiä tai tyhjän arvon, mikä vaikuttaa sen sisältävien elementtien tuottamaan tulokseen.
Jotta koodista saa selkeämmän rakenne-elementit kannattaa tuoda moduulin nimiavaruuteen:
local pt = require("Moduuli:ParametrisoituTeksti")
local ryhma, muuttuja, luettelo, tai = pt.ryhma, pt.muuttuja, pt.luettelo, pt.tai
muuttuja
[muokkaa]muuttuja(m)
Yksinkertaisin elementti, jolla merkitään ehdolliset kohdat eli ne kohdat, joilla joko on arvo tai ei ole arvoa.
Parametrit:
- Lua-muuttuja, joka sisältää merkkijonon tai arvon nil. Tyhjä merkkijono ja nil luetaan tyhjiksi.
local m1 = "eka"
local m2 = ""
local m3 = nil
ryhma("(", muuttuja(m1), ")") -- Tulos: "(eka)"
ryhma("(", muuttuja(m2), ")") -- Tulos: ""
ryhma("(", muuttuja(m3), ")") -- Tulos: ""
ryhma
[muokkaa]ryhma(prefiksi, elementti1, [erotin1, elementti2, [erotin2, elementti3...]], suffiksi)
Tärkein elementti, jolla merkitään ehdollista tekstiä.
Parametrit:
- Vaihtuva määrä parametreja.
- Ensimmäinen parametri on aina prefiksi ja viimeinen suffiksi. Prefiksi ja suffiksi tulostetaan, jos yksikin elementti on ei-tyhjä.
- Elementit: tässä luetelluilla rakenne-elementeillä merkittyjä alirakenteita.
- Erottimet: Merkkijonoja, jotka lisätään tulostukseen, jos niiden molemmilla puolilla olevilla muuttujilla on arvo. Erotinta voi edeltää numeroarvo, joka kertoo erottimen presedenssin toisiin erottiimiin nähden (oletusarvo on 0).
Esimerkkejä:
local m1 = "na"
local t1 = nil
ryhma("''", muuttuja(m1), "''-taivutus") -- tulos: "''na''-taivutus"
ryhma("''", muuttuja(t1), "''-taivutus") -- tulos: ""
local m1 = "eka"
local m2 = "toka"
local m3 = "kolkki"
local t1 = nil
ryhma("(", muuttuja(m1), ", ", muuttuja(m2), "; ", muuttuja(m3), ")") -- tulos: "(eka, toka; kolkki)"
ryhma("(", muuttuja(m1), ", ", muuttuja(m2), "; ", muuttuja(t1), ")") -- tulos: "(eka, toka)"
ryhma("(", muuttuja(t1), ", ", muuttuja(m2), "; ", muuttuja(m3), ")") -- tulos: "(toka; kolkki)"
ryhma("(", muuttuja(t1), ", ", muuttuja(m2), "; ", muuttuja(t1), ")") -- tulos: "(toka)"
ryhma("(", muuttuja(t1), ", ", muuttuja(t1), "; ", muuttuja(t1), ")") -- tulos: ""
-- Tässä tulokseen tulee puolipiste (;), koska sen sille on annettu suurempi presedenssi (1) kuin pilkulle (0).
ryhma("(", muuttuja(m1), ", ", muuttuja(t1), 1, "; ", muuttuja(m3), ")") -- tulos: "(eka; kolkki)"
luettelo
[muokkaa]luettelo(taulukko, erotin, viimeisen_erotin)
Erottimella erotellun luettelon tekemiseen.
Parametrit:
- taulukko lueteltavista elementeistä
- erotin, jolla arvot erotellaan
- toisiksi viimeisen ja viimeisen arvon välinen erotin, jos eri kuin erotin
local m1 = { "eka", "toka", "kolkki" }
luettelo(m1, ", ", " tai ") -- Tulos: "eka, toka tai kolkki"
local m1 = { "A", "B", nil, "D" }
local m2 = { "1", nil, "3", "4" }
luettelo(ryhma("", m1, " ", ryhma("(", m2, ")"), ""), ", ", " tai ") -- Tulos: "A (1), B, (3) tai D (4)"
Luetteloita voi olla myös sisäkkäin. Tällöin muuttujien pitää olla vastaavan syvyisiä puita.
- yksittäisessä luettelossa taulukko on muotoa { "1", "2", "3" },
- kun luettelo on toisen sisällä, taulukko on muotoa { { "1a", "1b" }, { "2a" }, { "3a", "3b" } },
- jne.
tai
[muokkaa]tai(elementti1, [elementti2, [elementti3...]]])
Lausekkeen tulos on ensimmäisen ei tyhjän rakenne-elementin arvo.
Parametrit:
- Mielivaltainen määrä muita rakenne-elementtejä.
local m1 = nil
local m2 = "toka"
local m3 = "kolkki"
tai(muuttuja(m1), muuttuja(m2)) -- Tulos: "toka"
tai(muuttuja(m2), muuttuja(m3)) -- Tulos: "toka"
funktio
[muokkaa]funktio(fun, param1, [param2, [param3...]]])
Tällä elementillä voi tehdä monimutkaisempia ehtoja, joita ei muilla elementeillä voi tehdä.
Parametrit:
- fun: funktio muotoa f(ctx, [param1, [param2, [param3...]]]), jossa ctx on viittaus muotoilija-olioon.
- muut parametrit: funktiolle mahdollisesti annettavat parametrit
Funktiossa pääse käsiksi parametrien arvoihin muotoilijaolion metodeilla hae_arvo ja hae_arvo_tai_nil.
Tekstiä lisätään tulostukseen lisäämällä muotoilijaolion out-kenttään.
Funktion pitää palauttaa true, jos tekstiä lisättiin, muuten false.
Huomaa, että se ovatko funktion parametrit elementtejä riippuu funktiosta.
Esim.
local function _sukuteksti(ctx, suku)
local lyh = ctx:hae_arvo_tai_nil(suku)
local txt = mw.getCurrentFrame():expandTemplate{ ['title'] = 'suku-teksti', ['args'] = { lyh } }
if txt then
table.insert(ctx.out, txt)
return true
end
return false
end
-----
local m1 = "f"
funktio(_sukuteksti, m1) -- Palauttaa mallinekutsun {{sukuteksti|f}} arvon.
Sanarivimallineissa usein esiintyviä toimintoja on koottuu moduuuliin LibSanarivi.
Huomaa, että alirakenteita voi myös nimetä käyttäen Luan funktioita apuna. Tässä ei kuitenkaan ole kyse funktioelementistä.
function p.tailuettelo(...)
return luettelo({...}, ", ", " tai ")
end
Muotoilu-olion metodit
[muokkaa]hae_arvo
[muokkaa]hae_arvo(m)
Palauttaa annetun parametrin arvon. Tätä käytetään funktio-elementissä. Arvoa ei pidä lukea suoraan ilman tätä metodia, koska metodi palauttaa oikean arvon myös silloin kun funktio on luettelon sisällä.
hae_arvo_tai_nil
[muokkaa]hae_arvo_tai_nil(m)
Sama kuin hae_arvo, mutta palauttaa nil myös, kun arvo on tyhjä merkkijono. Tämä on yleensä se, mitä halutaan.
prosessoi
[muokkaa]prosessoi(rakenne)
Lisää annetun elementtirakenteen tuottaman tekstin tulostukseen. Palauttaa true, jos tekstiä tulostettiin, muuten false.
Tätä voi kutsua funktio-elementissä, kun sille annetaan parametrina elementtirakenne.
Esimerkki tai-elementin toteutuksesta:
local function _tai(ctx, ...)
local params = {...}
local ret
for i = 1, #params do
ret = ctx:prosessoi(params[i])
if ret then
return true
end
end
return false
end
-- Käyttö:
funktio(_tai, luettelo(mon1, mon2, mon3, ", ", " ja "), muuttuja("ei monikkoa")) -- TODO tarkista
--- Moduuli tekstin muotoiluun.
local p = {}
function p:new (args)
local o = {
args = args,
-- Taulukko, johon "tulostetaan".
out = {},
-- Nykyinen sijainti luetteloissa. Esim. {2, 3} tarkoittaa toisen luettelon
-- kolmatta alkiota. Jokainen luettelo lisää uuden tason.
pos = {} }
setmetatable(o, self)
self.__index = self
return o
end
function p:uusi_muotoilija(args)
return p:new(args)
end
--- Muuttaa lopputuloksen merkkjonoksi.
function p:__tostring ()
return table.concat(self.out, "")
end
--- Palauttaa muuttujan sisäisen pos-jäsenen osoittaman arvon muuttujasta.
--
-- Esim.
-- Jos var = "a" ja pos = { }, palauttaa "a".
-- Jos var = { { "a1", "a2" }, { "b1" } } ja pos = { 2, 1 }, palauttaa "b1".
-- @param var: muuttuja
-- @return arvo. Jos arvoa ei ole tai se on tyhjä, palauttaa nil.
-- Jos osoite osoittaa syvemmälle kuin muuttujassa on kerroksia,
-- antaa virheen "odotettiin taulukkoarvoa". Jos osoite osoitaa
-- olemassa olevan kerroksen arvojen ulkopuolelle, palautta nil.
function p:hae_arvo(var)
-- Arvon osoite muuttujassa.
local pos = self.pos
local cur = var
if cur == nil then
return nil
end
for d = 1, #pos do
i = pos[d]
if cur == nil or ((type(cur) == "table" and i > #cur)) then
return nil
end
cur = cur[i]
end
if d ~= #pos and cur == nil then
error("odotettiin taulukkoarvoa kohdassa: [" .. table.concat(pos, ", ") .. "] löytyi: " .. var)
end
return cur
end
--- Sama kuin hae_arvo, mutta palauttaa nil, jos arvo on "".
--
-- @param var: muuttujan arvo
-- @return: kuten hae_arvo, mutta palauttaa nil jos arvo on tyhjä ("").
function p:hae_arvo_tai_nil(var)
local val = self:hae_arvo(var)
if val and val ~= "" then
return val
end
return nil
end
--- Lisää muttujan tulostukseen, jos se ei ole tyhjä.
--
-- @param ctx: konteksti
-- @param var: muuttujan arvo
-- @return: true, jos muuttuja lisättiin tulostukseen, muuten false.
local function _muuttuja(ctx, var)
local out = ctx.out
local val = ctx:hae_arvo(var)
if val and val ~= "" then
table.insert(out, val)
return true
else
return false
end
end
--- Ryhmä-toiminnon toteutus.
--
-- @param ctx: konteksti
-- @param ...: Taulukko, jonka ensimmäinen arvo on prefiksi ja viimeinen arvo suffiksi.
-- 2:sta eteenpäin joka toinen arvo on alirakenne tai muuttuja ja
-- joka toinen erotin. Erotinta voi kuitenkin edeltää numero, joka
-- kertoo sen presedenssin suhteessa toisiin erottimiin.
-- @return: true, jos yksikin alilauseke palautti true, muuten false.
local function _ryhma(ctx, ...)
local out = ctx.out
local kaava = {...}
local prefix_pos -- Prefiksin indeksi out-taulukossa.
local subval -- Alilausekkeen palauttama tulos (bool).
local retval = false -- Oma palautusarvo. Asetetaan trueksi, kun yksikin subval palauttaa true.
local sep -- Edellinen erotin.
local sep_prec = 0 -- Edellisen erottimen presedenssi.
local sep_pos = 0 -- Edellisen erottimen paikka out-taulukossa.
local odotus = "arvo" -- Arvo, jota odotetaan seuraavaksi ["arvo", "erotin"].
local prec = 0 -- Seuraavan erottimen presedenssi. Asetetaan, jos erotinta edeltää numero.
local cur -- Lausekkeen kohta, jossa ollaan.
-- Lisätään varaus prefiksille.
table.insert(out, "")
prefix_pos = #out
for i = 2, #kaava - 1 do
cur = kaava[i]
if odotus == "arvo" then -- Alilauseke tai muuttuja.
subval = ctx:prosessoi(cur)
-- Asetetaan trueksi ja pidetään truen, jos yksikin alilauseke on true.
retval = subval or retval
if subval and sep_pos > 0 then
out[sep_pos] = sep -- Asetetaan edellinen erotin.
sep_prec = 0
sep_pos = 0
end
odotus = "erotin"
elseif cur == tonumber(cur) then -- Presedenssiarvo.
prec = cur
else -- Erotin.
-- Asetetaan varaus erottimelle, jos aiemmin on ollut ainakin yksi arvo.
if retval and sep_prec <= prec then
table.insert(out, "")
sep_pos = #out
sep = cur
sep_prec = prec
end
prec = 0
odotus = "arvo"
end
end
if retval == true then
out[prefix_pos] = kaava[1] -- prefiksi
table.insert(out, kaava[#kaava]) -- suffiksi
end
return retval
end
--- Luettelotoiminnon toteutus.
--
-- @param ctx: konteksti
-- @param sub: toistettava alilauseke
-- @param sep: yleinen erotin
-- @param sepn: viimeistä edeltävä erotin
-- @return: true, jos yksikin alkio palautti true.
local function _luettelo(ctx, sub, sep, sepn)
local out = ctx.out
local pos = ctx.pos
-- Nykyisen ja edellisen erottimen kohta out-taulukossa.
local sep_pos, prev_sep_pos
local retval = false -- Oma paluuarvo.
local ret -- Alilausekkeiden paluuarvo.
-- Käytetään yleistä erotinta, jos erillistä viimeistä ei ole annettu.
sepn = sepn or sep
table.insert(pos, 1)
ret = ctx:prosessoi(sub)
while ret do
retval = true
prev_sep_pos = sep_pos
table.insert(out, sep)
sep_pos = #out
pos[#pos] = pos[#pos] + 1
ret = ctx:prosessoi(sub)
end
table.remove(pos)
if sep_pos then
out[sep_pos] = ""
if prev_sep_pos then
out[prev_sep_pos] = sepn
end
end
return retval
end
--- Tai-toiminnon toteutus.
--
-- @param ctx: konteksti
-- @param ...: taulukko vaihtoehdoista
-- @return: true, jos yksikin vaihtoehdoista palautti true,
-- false, muuten
local function _tai(ctx, ...)
local params = {...}
local ret
for i = 1, #params do
ret = ctx:prosessoi(params[i])
if ret then
return true
end
end
return false
end
--- Tutkii kaavan uloimman osan ja ohjaa sen oikealle käsittelijälle.
--
-- @param kaava: lauseke
function p:prosessoi(kaava)
if type(kaava) == "table" and kaava.funk ~= nil then
return kaava.funk(self, unpack(kaava.params))
else
return _muuttuja(self, kaava)
end
end
--- Peruskäyttöä yksinkertaistava funktio, joka muuttaa annetun rakenteen tekstiksi.
--
-- @param kaava: lauseke
-- @return: tulostettava teksti
function p.muotoile(kaava)
local m = p:uusi_muotoilija()
m:prosessoi(kaava)
return tostring(m)
end
---------------
-- Toiminnot --
---------------
--- Muuttuja (korvaava)
-- @param var: muuttujan arvo
function p.muuttuja(var)
return { ["funk"] = _muuttuja, ["params"] = { var } }
end
-- Tulostaa luettelon erottimilla erotettuna.
--
-- @param rak: toistettava rakenne
-- @param sep: yleinen erotin
-- @param sepn: (valinnainen) viimeistä edeltävä erotin
function p.luettelo(rak, sep, sepn)
return { ["funk"] = _luettelo, ["params"] = { rak, sep, sepn } }
end
--- Tulostaa parametrit prefiksillä ja suffiksillä ympäröitynä ja erottimilla erotettuna.
function p.ryhma(...)
return { ["funk"] = _ryhma, ["params"] = {...} }
end
--- Kokeilee vuorollaan jokaista annettua vaihtoehtoa kunnes joku palauttaa true.
function p.tai(...)
return { ["funk"] = _tai, ["params"] = {...} }
end
--- Muu funktio.
function p.funktio(funk, ...)
return { ["funk"] = funk, ["params"] = {...} }
end
return p