יחידה:אינפאקעסטל

פֿון װיקיפּעדיע
קפיצה לניווט קפיצה לחיפוש

אינפאקעסטל איז א מאדול וואס דינט צו שאפן אינפאקעסטל (Infobox) מוסטערן אין א גרינגען וועג מיט פארבינדונגען צו וויקידאטן.


local propertyLink = require('Module:PropertyLink')
local root
local args={}
local templateStructure = {}

--[[
Generate auto documentation for template.
]]
local function _generateDocumentation(frame) 
	local templateParams =  frame.args
	local labelDataPrefix = 'אינפא-עטיקעט'
	
	local parameters = {}
	for k,v in pairs(templateParams) do
		if mw.ustring.match( tostring(k),'תווית%-מידע%d' )  then
			table.insert(parameters, '"'..v..'":'..'{ "description": ""}')
		else
			for mm in mw.ustring.gmatch( tostring(v),'%{%{%{(.-)[%}|]') do
				table.insert(parameters, '"'..mm..'":'..'{ "description": ""}')
			end
		end
		
	end
	local templateDoc = '{ "params": { '..table.concat(parameters,'\n,')..'}}'
	return frame:extensionTag( 'templatedata', templateDoc )
end

--[[ 
Renders the infobox title
]]
local function renderTitle()
	-- renders the title
	return 	root
        :tag('caption')
            :addClass(args.titleclass)
            :cssText(args.titlestyle)
            :wikitext(args.title)
end

--[[ 
Renders the right/left images (possibly 1/2/none of them available) and the main image
]]
local function renderImages()
	-- render right an left images 
	args.rightImage = args.rightImage~=nil and #(args.rightImage)>0 and args.rightImage
	args.leftImage = args.leftImage~=nil and #(args.leftImage)>0 and args.leftImage
	
	if args.rightImage or args.leftImage then
		local row = root:tag('tr')
						:tag('td')
						:attr('colspan', 2)
						:css('text-align','center')
		if args.rightImage and args.leftImage then
			row:tag('table')
				:css('width','100%')
				:tag('tr')
					:tag('td')
						:css('width','50%')
						:css('vertical-align','middle')
						:wikitext(args.rightImage)
					:tag('td')
						:css('width','50%')
						:css('vertical-align','middle')
						:wikitext(args.leftImage)
					:done()
		else
			row:wikitext(args.leftImage or args.rightImage)
		end
	end
	-- render the main image
	if args.image then
		root:tag('tr')
			:tag('td')
			:attr('colspan', 2)
			:css('text-align','center')
			:wikitext(args.image)
		if args.imageDesc and #args.imageDesc>0 then
			root:tag('tr')
			:tag('td')
			:attr('colspan', 2)
			:addClass('thumbcaption')
			:css('text-align','center')
			:wikitext(args.imageDesc)
		end
		
	end
end

--[[ 
Adds edit links for easier editing of the template. If the template use data from wikidata it also adds edit link in Wikidata
]]
local function renderEditLinks()
	local wbEdit='' -- link to wikidata
	if args.usingWikidata then
		local entity = mw.wikibase.getEntityObject()
		wbEdit = '[[File:Wikidata-logo S.svg|20px|link=d:'..entity.id..'|לעריכה בוויקינתונים שמשמש מקור לחלק מהמידע בתבנית]]'
	end
	if #wbEdit > 0 then
		root:tag('tr')
			:tag('td')
			:attr('colspan', 2)
			:css('text-align','left')
			:wikitext(wbEdit)
	end
end

--[[ 
Adds a styled row to the table
]]
local function addRow(rowArgs)
    -- Adds a row to the infobox, with either a header cell
    -- or a label/data cell combination.
    if rowArgs.header then
        root
            :tag('tr')
                :addClass(rowArgs.rowclass)
                :cssText(args.rowsstyle)
                :cssText(rowArgs.rowstyle)
                :attr('id', rowArgs.rowid)
                :tag('th')
                    :attr('colspan', 2)
                    :attr('id', rowArgs.headerid)
                    :addClass(rowArgs.class)
                    :addClass(args.headerclass)
                    :css('text-align', 'center')
                    :cssText(args.headerstyle)
                    :wikitext(rowArgs.header)
    elseif rowArgs.data and #(rowArgs.data) > 0 then
        local row = root:tag('tr')
        row:addClass(rowArgs.rowclass)
           :cssText(args.rowsstyle)
           :cssText(rowArgs.rowstyle)
           :attr('id', rowArgs.rowid)
        if rowArgs.label then
            row
                :tag('th')
                    :attr('scope', 'row')
                    :attr('id', rowArgs.labelid)
                    :css('text-align', 'right')
                    :cssText(args.labelstyle)
                    :wikitext(rowArgs.label)
                    :done()
        end
 
        local dataCell = row:tag('td')
        if not rowArgs.label then 
            dataCell
                :attr('colspan', 2)
            if not rowArgs.datastyle then 
                dataCell:css('text-align', 'center') 
            end
        end
        dataCell
            :attr('id', rowArgs.dataid)
            :addClass(rowArgs.class)
            :cssText(rowArgs.datastyle)
            :newline()
            :wikitext(rowArgs.data)
    end
end
 
 --[[ 
This function removes redundent keys from templateStructure: nil entries and header entries with no data
]]
function removeEmptyHeaders()
 	local lastHeaderIndex=nil
 	local removeFirstHeader = (not args.image or #args.image==0) -- remove the first header if there is no image
	
 	local tempTemplateStructure = {}
 	for i,v in pairs(templateStructure) do
  		if v~=nil then
 			if v.header then
 				lastHeaderIndex = i
 			else
 				if lastHeaderIndex then
 					if not removeFirstHeader then
 						table.insert(tempTemplateStructure, templateStructure[lastHeaderIndex])
 					end
 					lastHeaderIndex = nil
 				end
 				removeFirstHeader = false
 				table.insert(tempTemplateStructure, v)
 			end
 		end
 	end
 	templateStructure=tempTemplateStructure
end
 
--[[ 
This function builds the infobox table using structure templateStructure and args
]]
function _infobox()
	removeEmptyHeaders()
	
	root = mw.html.create('table')
	root:addClass('infobox'):css('width', '18em'):cssText(args.tablestyle)
	renderTitle()
	renderImages()

	
	local infobox_rows={}
	for k,v in pairs(templateStructure) do
		addRow(v)
	end
	renderEditLinks()
	
	return tostring(root)
end

--[[ 
This function adds image using valueArg, or if not specified by the user tries to get image from wikidata using property
]]
function getValueOrWikidataImage(valueArg, wikidataArg,width)
	if valueArg and #valueArg>0 then return valueArg end
	if wikidataArg then 
		return propertyLink.getImageLink(wikidataArg, width)
	end
	return ''
	
end

--[[
This function fills missing parameter using wikidata
]]
function fillMissingParamFromWikidata(missingParam, templateParams, templateArg, frame)
	local inWikidata = false
	local maintainceCats = nil
	if templateParams[missingParam..'-וויקידאטן'] then
		templateArg.data = propertyLink.getProperty(templateParams[missingParam..'-וויקידאטן']) or nil
		inWikidata = templateArg.data and #(templateArg.data)>0
	elseif templateParams[missingParam..'-וויקידאטן-מרובה'] then
		templateArg.data = propertyLink.getProperty(templateParams[missingParam..'-וויקידאטן-מרובה'], true) or nil
		inWikidata = templateArg.data and #(templateArg.data)>0
	elseif templateParams[missingParam..'-וויקידאטן-פשוט'] then
		-- use data should be taken from wikidata and link must not be added
		local wikidataParamValue = propertyLink.getLabel(templateParams[missingParam..'-וויקידאטן-פשוט'])
		if wikidataParamValue and #wikidataParamValue>0 then
			templateArg.data = frame:preprocess(mw.ustring.gsub(templateArg.data, '\{\{\{('..missingParam..')\}\}\}', wikidataParamValue))
			inWikidata = true
		end
	elseif missingParam == 'קאארדינאטן' then
		templateArg.data = frame:expandTemplate{ title = 'קאארדינאטן פון וויקידאטן', args = { display = 'title,inline' } }
		inWikidata = templateArg.data and #(templateArg.data)>0
	end
	if inWikidata then
		local hasData =  #(mw.ustring.gsub(templateArg.data, '%[%[קאטעגאריע:.-%]%]', ''))>0
		if not hasData then
			inWikidata = false
			maintainceCats = templateArg.data
		end
	end

	return inWikidata, maintainceCats
end

function infobox(frame)
	local DEFAULT_IMAGE_PROPERTY = 'P18'
	local templateParams =  frame.args
	local templateArgs = frame:getParent().args
	args.title = frame.args['מוסטער קעפל']
	args.titlestyle = frame.args['מוסטער קעפל-עיצוב']
	args.titleclass = frame.args['מוסטער קעפל-מחלקה']
	args.rightImage = getValueOrWikidataImage(frame.args['תמונה ימין'], frame.args['תמונה ימין-וויקידאטן'], '100')
	args.leftImage = getValueOrWikidataImage(frame.args['תמונה שמאל'], frame.args['תמונה שמאל-וויקידאטן'], '100')
	args.image = getValueOrWikidataImage(frame.args['תמונה'], frame.args['תמונה-וויקידאטן'] or 'P18', '250')
	args.imageDesc = frame.args['כיתוב']
	args.headerclass = frame.args['קעפל-מחלקה']
	args.headerstyle = frame.args['קעפל-עיצוב']
    	args.rowsstyle = frame.args['שורה-עיצוב']
	args.tablestyle = frame.args['טבלה-עיצוב']
	local isSelfUse = (mw.title.getCurrentTitle().namespace==10)
	local autoDocumentation = frame.args['תיעוד-אוטומטי']

	local labelPrefix = 'תווית'
	local dataPrefix = 'מידע'
	local subheader = 'קעפל'
	local labelDataPrefix = 'תווית-מידע'
	local rowStylePrefix = 'עיצוב-שורה'
	local styleSuffix = '-עיצוב'
	local k=0
	local processedParams = {}
	local wikidataCats = {}
	for k,v in pairs(templateParams) do
		local i= string.match(k, '.-([0-9]+)$')
		if i and not (processedParams[i]) then
			indic = tonumber(i)
			processedParams[i]=1
			
			local subHeaderName = templateParams[subheader..i]
			if subHeaderName and #subHeaderName>0  then --subheader type
				table.insert(templateStructure, {header=subHeaderName,rowstyle=templateParams[rowStylePrefix..i], indic=indic})
			else
				local labelName = templateParams[labelPrefix..i]
				local dataTemplate = templateParams[dataPrefix..i]
				if labelName and dataTemplate then
					--label: data type
					table.insert(templateStructure, {label=labelName, data=dataTemplate, rowstyle=templateParams[rowStylePrefix..i], datastyle=templateParams[dataPrefix..i..styleSuffix], 
						labelstyle=templateParams[labelPrefix..i..styleSuffix], indic=indic})
				elseif labelName and not dataTemplate then
					--skip it. no only label [use subheader]
				elseif not labelName and dataTemplate then
					--only data type
					table.insert(templateStructure, {data=dataTemplate, rowstyle=templateParams[rowStylePrefix..i], datastyle=templateParams[dataPrefix..i..styleSuffix], indic=indic})
				else
					 local label_data_names = templateParams[labelDataPrefix..i]
					 if label_data_names then
					 	labelName = label_data_names
					 	label_data_names = mw.text.trim(label_data_names, '%[%]')
					 	if templateArgs[label_data_names] and #templateArgs[label_data_names]>0 then
					 		dataTemplate = templateArgs[label_data_names]
				 		else
				 			dataTemplate = '{{{' ..label_data_names.. '}}}'
					 	end
					 	table.insert(templateStructure, {label=labelName, data=dataTemplate, rowstyle=templateParams[rowStylePrefix..i], datastyle=templateParams[dataPrefix..i..styleSuffix], 
					 									 labelstyle=templateParams[labelPrefix..i..styleSuffix], indic=indic})
				 	end
				end
			end
		end
	end
	table.sort(templateStructure, function (x, y) return x.indic<y.indic end)
	
	-- use wikidata / remove unused parameters
	if not isSelfUse then
		for k,v in pairs(templateStructure) do
			if v.data then
				-- remove parameters that were explicitly defined to be removed
				local ignoreParam = mw.ustring.match(v.data, '^%-$')
				if ignoreParam then
					templateStructure[k]=nil
				else
					-- otherwise if the template isn't full - try to use wikidata to fill it
					local m = mw.ustring.match(v.data, '\{\{\{(.-)\}\}\}')
					if m then
						m = mw.uri.decode( m ) -- some templates may add encoding and are preprocessed before
						local inWikidata, maintainceCats = fillMissingParamFromWikidata(m, templateParams, v, frame)
						if maintainceCats then
							table.insert(wikidataCats, maintainceCats)
						end
						-- if data isn't available remove it
						if inWikidata then
							args.usingWikidata = true
						else
							templateStructure[k]=nil
						end
					end
				end
			end
	end
	
		-- use wikidata in title
		local m = mw.ustring.match(args.title, '\{\{\{(.-)\|?\}\}\}')
		if m then
			local inWikidata = false
			if templateParams[m..'-וויקידאטן'] then
				local wikidataParamValue = propertyLink.getProperty(templateParams[m..'-וויקידאטן']) or nil
				if wikidataParamValue then
					args.title = wikidataParamValue
				end
			elseif templateParams[m..'-וויקידאטן-פשוט'] then
				-- use data should be taken from wikidata and link must not be added
				local wikidataParamValue = propertyLink.getLabel(templateParams[m..'-וויקידאטן-פשוט'])
				if wikidataParamValue then
					args.title = frame:preprocess(mw.ustring.gsub(args.title, '\{\{\{('..m..')\|?\}\}\}', wikidataParamValue))
				end
			end
		end
	end

	if isSelfUse then
		local templateDocumentation=''
		for k,v in pairs(templateParams) do
			if mw.ustring.match( k, '-וויקידאטן') then
				templateDocumentation = templateDocumentation .. '[[קאטעגאריע:מוסטערן וואס ניצן וויקידאטן]]'
				break
			end
		end
		if autoDocumentation then
			templateDocumentation = templateDocumentation .. _generateDocumentation(frame)			
		end
		return _infobox() .. templateDocumentation
	end

	return _infobox() .. table.concat(wikidataCats, '')
end


return 	{
	['אינפאקעסטל']=infobox
}