Module:FormatSegmentRow: Difference between revisions
From Bodhicitta
(VSCode edit) |
(VSCode edit) |
||
| Line 222: | Line 222: | ||
if mw.smw then | if mw.smw then | ||
local pageTitle = mw.title.getCurrentTitle().prefixedText | local pageTitle = mw.title.getCurrentTitle().prefixedText | ||
local smwResult = mw.smw.ask( | local smwResult = mw.smw.ask('[[' .. pageTitle .. ']]|?SingleLanguage|?SingleColumn|limit=1') | ||
if smwResult and smwResult[1] then | if smwResult and smwResult[1] then | ||
if smwResult[1]['SingleLanguage'] then | if smwResult[1]['SingleLanguage'] then | ||
Revision as of 17:47, 1 April 2026
Documentation for this module may be created at Module:FormatSegmentRow/doc
local p = {}
-- TransMemID prefixes that indicate a non-English SegmentTranslation
local TRANSMEM_LANG = {
['004-Tsadra-BCA-Root-Padmakara-French'] = 'french',
['021-Tsadra-BCA-Padmakara-Spanish'] = 'spanish',
}
-- Build language table, routing SegmentTranslation to the correct language
-- based on TransMemID (defaults to english)
local function buildLanguages(transMemLang)
local englishParams = (transMemLang == 'english') and {'SegmentTranslation'} or {}
local frenchParams = (transMemLang == 'french') and {'SegmentTranslation', 'FrenchTranslation', 'French'} or {'FrenchTranslation', 'French'}
local spanishParams = (transMemLang == 'spanish') and {'SegmentTranslation', 'Spanish'} or {'Spanish'}
return {
{ id = 'tibetan', params = {'SegmentSource'}, classPrefix = 'tibetan-version', textClass = 'text-160', langType = 'source' },
{ id = 'tibetan-tsadra', params = {'SegmentSourceTsadra'}, classPrefix = 'tibetan-tsadra-version', textClass = 'text-160', langType = 'source' },
{ id = 'english', params = englishParams, classPrefix = 'english-version', textClass = 'text-article', langType = 'translation' },
{ id = 'wylie', params = {'SourceTranslit'}, classPrefix = 'wylie-version', textClass = 'text-article', langType = 'translation' },
{ id = 'wylie-tsadra', params = {'SegmentTranslitTsadra'}, classPrefix = 'wylie-tsadra-version', textClass = 'text-article', langType = 'translation' },
{ id = 'french', params = frenchParams, classPrefix = 'french-version', textClass = 'text-article', langType = 'translation' },
{ id = 'spanish', params = spanishParams, classPrefix = 'spanish-version', textClass = 'text-article', langType = 'translation' },
{ id = 'devanagari', params = {'SanskritSource'}, classPrefix = 'devanagari-version', textClass = 'text-160', langType = 'source' },
{ id = 'sanskrit', params = {'SanskritTranslit'}, classPrefix = 'sanskrit-version', textClass = 'text-article', langType = 'translation' },
}
end
-- Priority order for default visible language per side, given available params
local leftPriority = { 'tibetan', 'tibetan-tsadra', 'devanagari', 'wylie', 'wylie-tsadra', 'sanskrit' }
local rightPriority = { 'english', 'french', 'spanish', 'wylie', 'wylie-tsadra' }
-- Get first non-empty value from a list of param names
local function getParamValue(args, paramNames)
for _, name in ipairs(paramNames) do
local val = args[name]
if val and mw.text.trim(val) ~= '' then
return mw.text.trim(val)
end
end
return nil
end
-- Resolve default language for a side: first priority-list entry with content in args
local function resolveDefault(args, priorityList, languages)
local paramsByLang = {}
for _, lang in ipairs(languages) do
paramsByLang[lang.id] = lang.params
end
for _, id in ipairs(priorityList) do
local params = paramsByLang[id]
if params and #params > 0 and getParamValue(args, params) then
return id
end
end
return priorityList[1]
end
-- Convert semicolon-separated page names into wiki links
local function wikiLinkList(str)
local links = {}
for page in mw.text.gsplit(str, '%s*;%s*') do
if page ~= '' then
table.insert(links, '[[' .. page .. ']]')
end
end
return table.concat(links, ', ')
end
-- Wrap content with poem extension tag (for translation-side verse formats)
local function wrapPoem(frame, content)
return frame:extensionTag('poem', '<p class="m-0">' .. content .. '</p>')
end
-- Apply SegmentFormat styling to content
-- isSource: true for source-type languages, false for translation-type
local function formatContent(content, format, isSource, frame, sabcheNum, quoteSource)
if not content then return nil end
if format == 'Root' then
if isSource then
return '<div class="pl-4" style="color: #8c1409;"><p>' .. content .. '</p></div>'
else
return '<div class="p-bl-fix pl-4 my-2" style="color: #8c1409;"><p>' .. content .. '</p></div>'
end
elseif format == 'Title' then
if isSource then
return '<span class="text-130" style="color: #467083;">' .. content .. '</span>'
else
return '<div class="h3 font-serif-alt" style="color: #467083; white-space: break-spaces;">' .. content .. '</div>'
end
elseif format == 'Commentary' or format == 'Commentary2' or format == 'Colophon' then
return content
elseif format == 'Quote' then
local noteSuffix = ''
if quoteSource and quoteSource ~= '' then
noteSuffix = frame:expandTemplate{ title = 'note', args = { 'source', wikiLinkList(quoteSource) } }
end
if isSource then
return '<div class="pl-4" style="color: #897435;">' .. content .. noteSuffix .. '</div>'
else
return '<div class="pl-4" style="color: #897435;">' .. wrapPoem(frame, content .. noteSuffix) .. '</div>'
end
elseif format == 'DoubleQuote' or format == 'Verse inside a quote' then
local noteSuffix = ''
if quoteSource and quoteSource ~= '' then
noteSuffix = frame:expandTemplate{ title = 'note', args = { 'source', wikiLinkList(quoteSource) } }
end
if isSource then
return '<div class="pl-5" style="color: #897435;">' .. content .. noteSuffix .. '</div>'
else
return '<div class="pl-5" style="color: #897435;">' .. wrapPoem(frame, content .. noteSuffix) .. '</div>'
end
elseif format == 'Sabche' then
if isSource then
return '<span style="color: #467083;">' .. content .. '</span>'
else
local sabche = '<div class="p-bl-fix"><span style="color: #467083;">' .. content .. '</span>'
if sabcheNum then
sabche = sabche .. ' <span class="float-right">' .. sabcheNum .. '</span>'
end
return sabche .. '</div>'
end
elseif format == 'SabcheHeading' then
if isSource then
return '<div class="mt-3" style="color: #467083;">' .. content .. '</div>'
else
local heading = '<div class="h5 mt-3 font-serif-alt" style="color: #467083;">' .. content
if sabcheNum then
heading = heading .. ' <span class="float-right">' .. sabcheNum .. '</span>'
end
return heading .. '</div>'
end
elseif format == 'SabcheSubHeading' then
if isSource then
return '<div class="mt-2" style="color: #467083;">' .. content .. '</div>'
else
local subheading = '<div class="h6 mt-2 font-serif-alt" style="color: #467083;">' .. content
if sabcheNum then
subheading = subheading .. ' <span class="float-right">' .. sabcheNum .. '</span>'
end
return subheading .. '</div>'
end
elseif format == 'Section Title1' then
if isSource then
return content
else
return '<div class="h3 font-serif-alt" style="color: #467083; white-space: break-spaces;">' .. content .. '</div>'
end
elseif format == 'Section Title2' then
if isSource then
return '<span class="text-120" style="color: #467083;">' .. content .. '</span>'
else
return '<div class="h4 font-serif-alt" style="color: #467083; white-space: break-spaces;">' .. content .. '</div>'
end
elseif format == 'Indented Verse' then
if isSource then
return '<div class="pl-4">' .. content .. '</div>'
else
return '<div class="pl-4">' .. wrapPoem(frame, content) .. '</div>'
end
elseif format == 'Root non-verse' then
return '<span style="color: #8c1409;">' .. content .. '</span>'
else
-- Default: no special formatting
return content
end
end
-- Render all language divs for one side (left or right)
local function renderSide(args, side, format, frame, defaultLang, languages)
local sabcheNum = getParamValue(args, {'SourceSabcheNumber'})
local quoteSource = getParamValue(args, {'QuoteSource'})
local parts = {}
for _, lang in ipairs(languages) do
if #lang.params > 0 then
local content = getParamValue(args, lang.params)
if content then
local isSource = (lang.langType == 'source')
local formatted = formatContent(content, format, isSource, frame, sabcheNum, quoteSource)
if formatted then
local hidden = lang.id ~= defaultLang and ' hidden' or ''
local classes = 'toggleable ' .. lang.classPrefix .. '-' .. side .. ' ' .. lang.textClass .. hidden
table.insert(parts, '<div class="' .. classes .. '">' .. formatted .. '</div>')
end
end
end
end
return table.concat(parts)
end
function p.main(frame)
local args = frame:getParent().args
local format = getParamValue(args, {'SegmentFormat'}) or 'Commentary'
-- Determine which language SegmentTranslation holds based on TransMemID
local transMemId = getParamValue(args, {'TransMemID'}) or ''
local transMemLang = TRANSMEM_LANG[transMemId] or 'english'
local languages = buildLanguages(transMemLang)
local defaultLeft = resolveDefault(args, leftPriority, languages)
local defaultRight = resolveDefault(args, rightPriority, languages)
-- Fetch SingleLanguage and SingleColumn from the current page in one SMW call
local singleLang = nil
local singleColumn = false
if mw.smw then
local pageTitle = mw.title.getCurrentTitle().prefixedText
local smwResult = mw.smw.ask('[[' .. pageTitle .. ']]|?SingleLanguage|?SingleColumn|limit=1')
if smwResult and smwResult[1] then
if smwResult[1]['SingleLanguage'] then
singleLang = mw.text.trim(tostring(smwResult[1]['SingleLanguage'])):lower()
end
if smwResult[1]['SingleColumn'] then
local scVal = mw.text.trim(tostring(smwResult[1]['SingleColumn'])):lower()
singleColumn = (scVal == 'true' or scVal == '1' or scVal == 't')
end
end
end
-- Determine which side the single language lives on
local singleIsLeft = singleLang and (function()
for _, id in ipairs(leftPriority) do if id == singleLang then return true end end
end)()
local singleIsRight = singleLang and (function()
for _, id in ipairs(rightPriority) do if id == singleLang then return true end end
end)()
-- Filter languages to only the requested one when in single-language mode
local function filterLanguages(langs, targetId)
local filtered = {}
for _, lang in ipairs(langs) do
if lang.id == targetId then
table.insert(filtered, lang)
end
end
return filtered
end
local output = ''
if singleColumn then
-- Single-column mode: all available languages in one col-12, left-side classes.
-- The language switcher (RootVerseToggles) still works since the togglable divs
-- use the same tibetan-version-left / wylie-version-left etc. class names.
local content = renderSide(args, 'left', format, frame, defaultLeft, languages)
output = '<div class="col-12 font-serif line14 p-bl-fix mb-3">' .. content .. '</div>'
elseif singleLang then
-- Single-language mode: render only the matching column at full width
if singleIsLeft then
local filteredLangs = filterLanguages(languages, singleLang)
local content = renderSide(args, 'left', format, frame, singleLang, filteredLangs)
output = '<div class="col-12 font-serif line14 p-bl-fix mb-3">' .. content .. '</div>'
elseif singleIsRight then
local filteredLangs = filterLanguages(languages, singleLang)
local content = renderSide(args, 'right', format, frame, singleLang, filteredLangs)
output = '<div class="col-12 line14 p-bl-fix mb-3">' .. content .. '</div>'
else
-- Unknown language id: fall back to normal two-column layout
local left = renderSide(args, 'left', format, frame, defaultLeft, languages)
local right = renderSide(args, 'right', format, frame, defaultRight, languages)
output = '<div class="col-md-6 font-serif line14 p-bl-fix mb-3">' .. left .. '</div>'
.. '<div class="col-md-6 line14 p-bl-fix mb-3">' .. right .. '</div>'
end
else
-- Normal two-column layout
local left = renderSide(args, 'left', format, frame, defaultLeft, languages)
local right = renderSide(args, 'right', format, frame, defaultRight, languages)
output = '<div class="col-md-6 font-serif line14 p-bl-fix mb-3">' .. left .. '</div>'
.. '<div class="col-md-6 line14 p-bl-fix mb-3">' .. right .. '</div>'
end
return output
end
return p