local p = {}
local mError = require('Module:Error').error
local fullurl = require('Module:Fullurl')._fullurl
local gFrame = mw.getCurrentFrame()
local useLang = gFrame:callParserFunction{ name = 'int', args = {'Lang'} }
local isHeadingHTMLChange = false -- https://www.mediawiki.org/wiki/Heading_HTML_changes
local function buildEditLink(sectionEditLinkData)
local sectionId, sectionName
local title = sectionEditLinkData.title
if sectionEditLinkData.sectionId then
sectionId = sectionEditLinkData.sectionId
sectionName = sectionEditLinkData.sectionName or p.getSectionNameByID(title, sectionId)
else
sectionName = sectionEditLinkData.sectionName
sectionId = p.getSectionIDByName(title, sectionName)
end
return mw.html.create('span'):addClass('mw-editsection plainlinks')
:node(mw.html.create('span'):addClass('mw-editsection-bracket'):wikitext('['))
:wikitext(
fullurl({
title = title,
action = 'edit',
section = sectionId,
text = tostring(
mw.html.create('span')
:attr('title', mw.message.new('editsectionhint', {sectionName}):inLanguage(useLang):plain())
:wikitext(mw.message.new('editsection', {title}):inLanguage(useLang):plain())
:done()
)
})
)
:node(mw.html.create('span'):addClass('mw-editsection-bracket'):wikitext(']'))
:done()
end
local function buildFakeHOld(text, level, id, sectionEditLinkData)
local wrapper = mw.html.create('h' .. id)
local headline = wrapper:tag('span'):addClass('mw-headline')
if id then
headline = headline:attr('id', id)
end
if sectionEditLinkData then
wrapper:node(buildEditLink(sectionEditLinkData))
end
return wrapper:done()
end
local function buildFakeHNew(text, level, id, sectionEditLinkData)
local wrapper = mw.html.create('span'):addClass('mw-heading mw-heading' .. level)
local headline = wrapper:tag('h' .. level)
if id then
headline = headline:attr('id', id)
end
if sectionEditLinkData then
wrapper:node(buildEditLink(sectionEditLinkData))
end
return wrapper:done()
end
local function buildFakeH(...)
return (isHeadingHTMLChange and buildFakeHNew or buildFakeHOld)(...)
end
local function indexOf(arr, str)
if not arr then
return -1
end
for i, v in ipairs(arr) do
if str == v then
return i
end
end
return -1
end
function p.getSectionsList(title)
title = mw.title.new(title, '')
if title then
if not title:getContent() then
return nil
end
local wikitext = title:getContent():gsub('{{[^}]+}}', ''):gsub('{%|(.-)%|}', '')
local sections = {}
local match = wikitext:match('%=([^\n]+)%=')
while true do
if not match then
break
end
match = '=' .. match .. '='
sections[#sections + 1] = mw.text.trim(match:gsub('^%=+([^\n%=]+)%=+$', '%1'), '\t\r\n\f%s')
wikitext = wikitext:gsub(match, '')
match = wikitext:match('%=([^\n]+)%=')
end
return sections
end
return nil
end
function p.getSectionIDByName(title, section)
if section == '__FIRST_SECTION__' then
return 0
end
return indexOf(p.getSectionsList(title), section) or -1
end
function p.getSectionNameByID(title, section)
if tonumber(section) == 0 then
return '首段'
end
return p.getSectionsList(title)[section] or ''
end
function p._main(text, configs)
local frame = mw.getCurrentFrame()
local level, id, title, sectionEditLinkData
if type(configs) == 'string' then
level = tonumber(configs)
else
level = tonumber(configs.level)
id = configs.id
if configs.editlink then
if type(configs.editlink) == type('') then
local preTitle, preSection
for k, v in configs.editlink:gmatch("([^#]*)#(.+)") do
preTitle = mw.text.trim(k)
preSection = mw.text.trim(v)
break
end
if preTitle ~= nil then
sectionEditLinkData = {
title = preTitle ~= '' and mw.title.new(preTitle).fullText or mw.title.getCurrentTitle().fullText,
sectionName = preSection
}
else
for k, v in configs.editlink:gmatch("([^,]+),(.+)") do
preTitle = mw.text.trim(k)
preSection = mw.text.trim(v)
break
end
if preTitle ~= nil then
if tonumber(preSection) ~= nil then
sectionEditLinkData = {
title = preTitle ~= '' and mw.title.new(preTitle).fullText or mw.title.getCurrentTitle().fullText,
sectionId = tonumber(preSection)
}
else
sectionEditLinkData = {
title = preTitle ~= '' and mw.title.new(preTitle).fullText or mw.title.getCurrentTitle().fullText,
sectionName = preSection
}
end
end
end
elseif configs.editlink.section then
if tonumber(configs.editlink.section) then
sectionEditLinkData = {
title = configs.editlink.title ~= '' and mw.title.new(configs.editlink.title).fullText or mw.title.getCurrentTitle().fullText,
sectionId = tonumber(configs.editlink.section)
}
else
sectionEditLinkData = {
title = configs.editlink.title ~= '' and mw.title.new(configs.editlink.title).fullText or mw.title.getCurrentTitle().fullText,
sectionName = configs.editlink.section
}
end
else
sectionEditLinkData = configs.editlink
sectionEditLinkData.title = sectionEditLinkData.editlink.title ~= ''
and mw.title.new(sectionEditLinkData.editlink.title).fullText
or mw.title.getCurrentTitle().fullText
end
end
end
if not level or indexOf({1, 2, 3, 4, 5, 6}, level) == -1 then
return mError({[1] = '無法解釋章節等級' .. tostring(frame:extensionTag('syntaxhighlight', '<h' .. level .. '></h' .. level .. '>', {lang = 'html', inline = ''}))})
end
return buildFakeH(text, level, id, sectionEditLinkData)
end
function p.main(frame)
local text = ''
local getArgs = require('Module:Arguments').getArgs
local configs = getArgs(frame, {
frameOnly = true
})
local args = getArgs(frame, {
removeBlanks = false,
valueFunc = (function (key, value)
if key == 1 then
return value
end
return nil
end),
parentFirst = true
})
if not args[1] then
text = '標題'
else
text = args[1]
end
if args['editlink'] then
configs['editlink'] = args['editlink']
end
if args['id'] then
configs['id'] = args['id']
end
return p._main(text, configs)
end
return p