Ir al contenido

Módulo:mostrar-unicode

De Wikcionario, el diccionario libre
Documentación del módulo
Usado por Plantilla:mostrar-unicode, a su vez requiere de Módulo:unicode-base. Basado en el módulo {{character info}} del Wiktionary en inglés (se agradece).
Esta documentación está transcluida desde Módulo:mostrar-unicode/doc.
Los editores pueden experimentar en la zona de pruebas de este módulo.
Por favor, añade las categorías e interwikis a la subpágina de documentación. Subpáginas de este módulo.
-- tomado de en.wiktionary.org/wiki/Module:character_info

local m_str = require("Módulo:string")
local u = m_str.char
local cp = m_str.codepoint
local gcodepoint = m_str.gcodepoint
local len = m_str.len
local encodehtml = m_str.encodehtml
local toNFD = m_str.toNFD

local m_unicode = require('Módulo:unicode-base')

local char_to_script = require('Módulo:scripts/charAScript').charAScript

local m_scripts = require('Módulo:scripts')
local sc_get_by_code = m_scripts.getByCode

local floor = math.floor -- ver hangul
local insert = table.insert
local concat = table.concat

local export = {}

local function get_codepoint(codepoint, param_name)
	if type(codepoint) == "string" and len(codepoint) == 1 then
		return cp(codepoint)
	end
	local codepointnum = tonumber(codepoint) -- or decode_entities(codepoint), no aplica para esta wiki
	if type(codepointnum) ~= "number" then
		error("Unrecognised string given for the " .. param_name .. " parameter")
	end
	return codepointnum
end

local function _show(pagename, ns, frame, codepoint, mdc, egpz, gardiner)
	if codepoint then
		codepoint = get_codepoint(codepoint, "codepoint")
	elseif len(pagename) == 1 then
		codepoint = cp(pagename)
	else
		error("Page title is not a single Unicode character ("..tostring(len(pagename))..")")
	end

	local image = m_unicode.lookup_image(codepoint)
	local image_emoji = m_unicode.lookup_image_emoji(codepoint)

	local table_markup = {}
	insert(table_markup, frame:extensionTag("templatestyles", nil, {src = "Plantilla:mostrar-unicode/estilo.css"}).."\n")
	insert(table_markup, '{| class="wikitable mostrar-unicode"\n')

	if image or image_emoji then
		-- local category = "[[Categoría:Caracteres imagen|*" .. string.format("%010d", codepoint) .. "]]"
		local category = ""
		if image and not image:match("\127") then -- <hiero> tags generate these; pass them through
			assert(not image:find("%[]|"))
			image = "[[File:" .. image .. "|120x140px|class=skin-invert-image]]"
			if ns == 0 then
				image = image .. category
			end
		end

		if image_emoji then
			if image then
				insert(table_markup,
					'|-\n! Estilo texto !! Estilo emoji\n')
			end
			assert(not image_emoji:find("%[]|"))
			image_emoji = "[[File:" .. image_emoji .. "|120x140px|class=skin-invert-image]]"
			if ns == 0 and not image then
				image_emoji = image_emoji .. category
			end
			if image then
				insert(table_markup,
					('|-\n| style="text-align: center; width: 50%s;" | %s || style="text-align: center; width: 50%s;" | %s\n'):format(
						'%', image, '%', image_emoji
					)
				)
			else
				insert(table_markup,
					('|-\n| colspan="2" style="text-align: center;" | %s\n'):format(
						image_emoji
					)
				)
			end
		else
			insert(table_markup,
				('|-\n| colspan="2" style="text-align: center;" | %s\n'):format(
					image
				)
			)
		end
	end

	local show_different_styles_if_no_emoji_image = false
	-- https://en.wikipedia.org/wiki/List_of_emojis

	-- Basic Latin (see https://en.wikipedia.org/wiki/Basic_Latin_(Unicode_block)#Variants)
	if codepoint == 35 or codepoint == 42 or (codepoint > 47 and codepoint < 58)
	-- Latin-1 Supplement
	or codepoint == 169 or codepoint == 174
	-- General Punctuation
	or codepoint == 8252 or codepoint == 8265
	-- Letterlike Symbols
	or codepoint == 8482 or codepoint == 8505
	-- Arrows
	or (codepoint > 8595 and codepoint < 8602) or codepoint == 8617 or codepoint == 8618
	-- Miscellaneous Technical
	or codepoint == 8986 or codepoint == 8987 or codepoint == 9000 or codepoint == 9167 or (codepoint > 9192 and codepoint < 9204) or (codepoint > 9207 and codepoint < 9211)
	-- Enclosed Alphanumerics
	or codepoint == 9410
	-- Geometric Shapes
	or codepoint == 9642 or codepoint == 9643 or codepoint == 9654 or codepoint == 9664 or (codepoint > 9722 and codepoint < 9727)
	-- Miscellaneous Symbols
	or (codepoint > 9727 and codepoint < 9733) or codepoint == 9742 or codepoint == 9745 or codepoint == 9748 or codepoint == 9749 or codepoint == 9752 or codepoint == 9757 or codepoint == 9760 or codepoint == 9762 or codepoint == 9763 or codepoint == 9766 or codepoint == 9770 or codepoint == 9774 or codepoint == 9775 or (codepoint > 9783 and codepoint < 9787) or codepoint == 9792 or codepoint == 9794 or (codepoint > 9799 and codepoint < 9812) or codepoint == 9823 or codepoint == 9824 or codepoint == 9827 or codepoint == 9829 or codepoint == 9830 or codepoint == 9832 or codepoint == 9851 or codepoint == 9854 or codepoint == 9855 or (codepoint > 9873 and codepoint < 9880) or codepoint == 9881 or codepoint == 9883 or codepoint == 9884 or codepoint == 9888 or codepoint == 9889 or codepoint == 9895 or codepoint == 9898 or codepoint == 9899 or codepoint == 9904 or codepoint == 9905 or codepoint == 9917 or codepoint == 9918 or codepoint == 9924 or codepoint == 9925 or codepoint == 9928 or codepoint == 9934 or codepoint == 9935 or codepoint == 9937 or codepoint == 9939 or codepoint == 9940 or codepoint == 9961 or codepoint == 9962 or (codepoint > 9967 and codepoint < 9974) or (codepoint > 9974 and codepoint < 9979) or codepoint == 9981
	-- Dingbats
	or codepoint == 9986 or codepoint == 9989 or (codepoint > 9991  and codepoint < 9998) or codepoint == 9999 or codepoint == 10002 or codepoint == 10004 or codepoint == 10006 or codepoint == 10013 or codepoint == 10017 or codepoint == 10024 or codepoint == 10035 or codepoint == 10036 or codepoint == 10052 or codepoint == 10055 or codepoint == 10060 or codepoint == 10062 or (codepoint > 10066 and codepoint < 10070) or codepoint == 10071 or codepoint == 10083 or codepoint == 10084 or (codepoint > 10132 and codepoint < 10136) or codepoint == 10145 or codepoint == 10160 or codepoint == 10175
	-- Supplemental Arrows-B
	or codepoint == 10548 or codepoint == 10549
	-- Miscellaneous Symbols and Arrows
	or (codepoint > 11012 and codepoint < 11016) or codepoint == 11035 or codepoint == 11036 or codepoint == 11088 or codepoint == 11093
	-- CJK Symbols and Punctuation
	or codepoint == 12336 or codepoint == 12349
	-- Enclosed CJK Letters and Months
	or codepoint == 12951 or codepoint == 12953
	-- Mahjong Tiles
	or codepoint == 126980
	-- Playing Cards
	or codepoint == 127183
	-- Enclosed Alphanumeric Supplement
	or codepoint == 127344 or codepoint == 127345 or codepoint == 127358 or codepoint == 127359 or codepoint == 127374 or (codepoint > 127376 and codepoint < 127387)
	-- Enclosed Ideographic Supplement
	or codepoint == 127489 or codepoint == 127490 or codepoint == 127514 or codepoint == 127535 or (codepoint > 127537 and codepoint < 127547) or codepoint == 127568 or codepoint == 127569
	-- Miscellaneous Symbols and Pictographs
	or (codepoint > 127743 and codepoint < 127778) or (codepoint > 127779 and codepoint < 127892) or codepoint == 127894 or codepoint == 127895 or (codepoint > 127896 and codepoint < 127900) or (codepoint > 127901 and codepoint < 127985) or (codepoint > 127986 and codepoint < 127990) or (codepoint > 127990 and codepoint < 128254) or (codepoint > 128254 and codepoint < 128318) or (codepoint > 128328 and codepoint < 128335) or (codepoint > 128335 and codepoint < 128360) or codepoint == 128367 or codepoint == 128368 or (codepoint > 128370 and codepoint < 128379) or codepoint == 128391 or (codepoint > 128393 and codepoint < 128398) or codepoint == 128400 or codepoint == 128405 or codepoint == 128406 or codepoint == 128420 or codepoint == 128421 or codepoint == 128424 or codepoint == 128433 or codepoint == 128434 or codepoint == 128444 or (codepoint > 128449 and codepoint < 128453) or (codepoint > 128464 and codepoint < 128468) or (codepoint > 128475 and codepoint < 128479) or codepoint == 128481 or codepoint == 128483 or codepoint == 128488 or codepoint == 128495 or codepoint == 128499 or (codepoint > 128505 and codepoint < 128512)
	-- Emoticons
	or (codepoint > 128511 and codepoint < 128592)
	-- Transport and Map Symbols
	or (codepoint > 128639 and codepoint < 128710) or (codepoint > 128714 and codepoint < 128723) or (codepoint > 128724 and codepoint < 128732) or (codepoint > 128731 and codepoint < 128742) or codepoint == 128745 or codepoint == 128747 or codepoint == 128748 or codepoint == 128752 or (codepoint > 128754 and codepoint < 128765)
	-- Geometric Shapes Extended
	or (codepoint > 128991 and codepoint < 129004) or codepoint == 129008
	-- Supplemental Symbols and Pictographs
	or (codepoint > 129291 and codepoint < 129339) or (codepoint > 129339 and codepoint < 129350) or (codepoint > 129350 and codepoint < 129536)
	-- Symbols and Pictographs Extended-A
	or (codepoint > 129647 and codepoint < 129661) or (codepoint > 129663 and codepoint < 129673) or (codepoint > 129679 and codepoint < 129726) or (codepoint > 129726 and codepoint < 129734) or (codepoint > 129741 and codepoint < 129756) or (codepoint > 129759 and codepoint < 129769) or (codepoint > 129775 and codepoint < 129785)
	then
		show_different_styles_if_no_emoji_image = true
	end
	if show_different_styles_if_no_emoji_image and not (image and image_emoji) then
		insert(table_markup,
			'|-\n! Estilo texto !! Estilo emoji\n')
	end
	if show_different_styles_if_no_emoji_image or image_emoji or m_unicode.lookup_image_emoji(codepoint) then
		insert(table_markup,
			('|- style="font-size: 250%; text-align: center;"\n| style="padding: 0;" | ' .. u(codepoint) .. '&#xFE0E; || style="padding: 0;" | ' .. u(codepoint) .. '&#xFE0F;\n|- style="font-size: 80%;"\n| colspan="2" | El estilo texto se puede [[selector de variante|forzar]] con ⟨&amp;#xFE0E;⟩, mientras que el estilo emoji se fuerza con ⟨&amp;#xFE0F;⟩.\n')
		)
	end

	local script_code = char_to_script(codepoint)
	local script_data = sc_get_by_code(script_code) or error("No data for script code " .. script_code .. ".")
	local script_name = script_data._data[1]

	local cat_name
	if script_data._data.character_category ~= false then
		cat_name = "Caracteres del script "..script_name or nil
	end
	local block_name = encodehtml(m_unicode.lookup_block(codepoint))

	local function parse_aliases(aliases)
		local result = {}

		if aliases then
			local classif = {}
			for i, alias in ipairs(aliases) do
				if not classif[alias[1]] then
					classif[alias[1]] = {}
				end
				insert(classif[alias[1]], encodehtml(alias[2]))
			end

			if classif.correction then
				for i, name in ipairs(classif.correction) do
					local category = '[[Categoría:Caracteres con nombres cambiados]]'
					if ns == 0 then
						insert(result,
							(category..'Corregido: %s'):format(
								name
							)
						)
					else
						insert(result,
							('Corregido: %s'):format(
								name
							)
						)
					end
				end
			end

			if classif.alternate then
				for i, name in ipairs(classif.alternate) do
					local category = '[[Categoría:Caracteres con nombres alternativos]]'
					if ns == 0 then
						insert(result,
							(category..'Alternativo: %s'):format(
								name
							)
						)
					else
						insert(result,
							('Alternativo: %s'):format(
								name
							)
						)
					end
				end
			end

			if classif.abbreviation then
				local category = '[[Categoría:Caracteres con abreviaturas]]'
				if ns == 0 then
					insert(result,
						(category..'Abreviatura: %s'):format(
							concat(classif.abbreviation, ", ")
						)
					)
				else
					insert(result,
						('Abreviatura: %s'):format(
							concat(classif.abbreviation, ", ")
						)
					)
				end
			end

			local parsed_result = concat(result, ", ")

			return '<div>(' .. parsed_result .. ')</div>'

		end

		return ""

	end

	local li, vi, ti = nil, nil, nil

	if block_name == "Sílabas hangul" then
		local index = codepoint - 0xAC00
		li, vi, ti = floor(index / 588), floor((index % 588) / 28), index % 28
	end

	local initial_to_letter = { [0] =
		0x3131, 0x3132, 0x3134, 0x3137, 0x3138, 0x3139, 0x3141, 0x3142,
		0x3143, 0x3145, 0x3146, 0x3147, 0x3148, 0x3149, 0x314A, 0x314B,
		0x314C, 0x314D, 0x314E,
	}

	local vowel_to_letter = { [0] =
		0x314F, 0x3150, 0x3151, 0x3152, 0x3153, 0x3154, 0x3155, 0x3156,
		0x3157, 0x3158, 0x3159, 0x315A, 0x315B, 0x315C, 0x315D, 0x315E,
		0x315F, 0x3160, 0x3161, 0x3162, 0x3163,
	}

	local final_to_letter = {
		0x3131, 0x3132, 0x3133, 0x3134, 0x3135, 0x3136, 0x3137, 0x3139,
		0x313A, 0x313B, 0x313C, 0x313D, 0x313E, 0x313F, 0x3140, 0x3141,
		0x3142, 0x3144, 0x3145, 0x3146, 0x3147, 0x3148, 0x314A, 0x314B,
		0x314C, 0x314D, 0x314E,
	}

	local function parse_composition()

		local result = nil

		if block_name == "Sílabas hangul" then

			result = ((ti ~= 0) and
				'<big class="Kore" lang="">[[&#%u;]] + [[&#%u;]] + [[&#%u;]]</big>' or
				'<big class="Kore" lang="">[[&#%u;]] + [[&#%u;]]</big>'):format(
					initial_to_letter[li],
					vowel_to_letter[vi],
					final_to_letter[ti]
				)

		else
			local nfd = toNFD(u(codepoint))
			if len(nfd) ~= 1 then
				local compo = {}

				for nfdcp in gcodepoint(nfd)	do

					local dotted_circle = (m_unicode.is_combining(nfdcp) and "◌" or "")
					local link_target = m_unicode.get_entry_title(nfdcp)
					local script = char_to_script(nfdcp)

					local character_text =
						link_target and ('[[%s|<span class="%s">%s&#%u;</span> &#91;U+%04X&#93;]]')
									:format(link_target, script, dotted_circle, nfdcp, nfdcp)
						or ('<span class="%s">%s&#%u;</span> &#91;U+%04X&#93;')
									:format(script, dotted_circle, nfdcp, nfdcp)

					insert(compo, '<span class="character-sample-secondary">' .. character_text .. '</span> ')
				end

				result = concat(compo, " + ")

			end
		end

		if result then
			return "Composition", result, "[[Categoría:Caracteres compuestos]]"
		end

		return nil
	end

	-- [[ Egyptian Hieroglyphs
	local function parse_gardiner()
		if gardiner then
			return "Gardiner number", ('[http://vincent.euverte.free.fr/Rosette/Rosette_410.php?Hiero=%s&Lang=E %s]\n'):format(gardiner, gardiner), "[[Categoría:Jeroglíficos egipcios]]"
		end

		return nil
	end

	local function parse_mdc()
		if mdc then
			return "Manuel de Codage", mdc, "[[Categoría:Jeroglíficos egipcios]]"
		end

		return nil
	end

	local function parse_egpz()
		if egpz then
			return "EGPZ 1.0", egpz, "[[Categoría:Jeroglíficos egipcios]]"
		end

		return nil
	end

	-- ]]

	local function middle_part()
		local rows = {}

		local function insert_row(row_title, row_contents, row_category)
			if row_contents then
				insert(rows, ('<tr><td style="text-align: left">%s:</td><td>%s%s</td></tr>'):format(row_title, row_contents, row_category))
			end
		end

		insert_row(parse_composition())
		insert_row(parse_gardiner())
		insert_row(parse_egpz())
		insert_row(parse_mdc())

		if rows[1] then
			return ('<table style="margin: 0 auto;">%s</table>'):format(concat(rows, ""))
		end

		return ""
	end

	local function present_codepoint(cpt, np)
		local display = ""
		local link_target = m_unicode.get_entry_title(cpt)
		local combining = m_unicode.is_combining(cpt)
		local printable = m_unicode.is_printable(cpt)
		local name = m_unicode.lookup_name(cpt)
		local script = char_to_script(cpt)

		if printable then
			display = ('<span class="character-sample-secondary %s">%s&#x%04X;</span>'):format(
				script,
				combining and "◌" or "", cpt
			)
		end

		local arrow_and_maybe_char
		if np then
			arrow_and_maybe_char = display .. ' →'
		else
			arrow_and_maybe_char = '← ' .. display
		end

		local text = ('<span title="%s">%s<br><small>[U+%04X]</small></span>')
			:format(encodehtml(name),
				arrow_and_maybe_char, cpt)

		if link_target then
			return ('[[' .. link_target .. '|' .. text .. ']]')
		else
			return text
		end
	end

	local function get_next(cpt, step)
		-- Skip past noncharacters and reserved characters (Cn), private-use
		-- characters (Co), surrogates (Cs), and control characters (Cc), all
		-- of which have a label beginning in "<" rather than a proper name.
		if step < 0 and 0 < cpt or step > 0 and cpt < 0x10FFFF then
			repeat
				cpt = cpt + step
			until m_unicode.lookup_name(cpt):sub(1, 1) ~= "<"
				or not (0 < cpt and cpt < 0x10FFFF)
		end

		return cpt
	end


	local previous_codepoint = get_next(codepoint, -1)
	local next_codepoint = get_next(codepoint, 1)
	local combining = m_unicode.is_combining(codepoint)

	insert(table_markup,
		'|-\n| style="width: 70px;" colspan="2" | ' ..
		'<table>' ..
		'<tr>' ..
		'<td>' ..
			('<span class="character-sample-primary %s">%s&#%u;</span>')
				:format(script_code, combining and "◌" or "", codepoint) ..
		'</td>' ..
		'<td>' ..
			(' [https://util.unicode.org/UnicodeJsps/character.jsp?a=%.4X U+%.4X]'):format(codepoint, codepoint) ..
			', [[w:Anexo:Referencias_a_entidades_de_caracteres_XML_y_HTML|&amp;#' .. codepoint .. ';]]\n' ..
		'<div class="character-sample-name">' ..
		encodehtml(m_unicode.lookup_name(codepoint)) ..
		'</div>' ..
		parse_aliases(mw.loadData('Módulo:unicode-base/alias')[codepoint]) ..
		'</td>' ..
		'</tr>' ..
		'</table>'
	)

	insert(table_markup,middle_part())

	local previous_unassigned_first = previous_codepoint + 1
	local previous_unassigned_last = codepoint - 1
	local next_unassigned_first = codepoint + 1
	local next_unassigned_last = next_codepoint - 1

	local left_unassigned_text
	local right_unassigned_text

	if previous_codepoint == 0 then
		previous_unassigned_first = 0
	end

	if previous_unassigned_first <= previous_unassigned_last or next_unassigned_first <= next_unassigned_last then
		if previous_unassigned_first < previous_unassigned_last then
			left_unassigned_text = ('[sin asignar: U+%.4X–U+%.4X]'):format(previous_unassigned_first, previous_unassigned_last)
		elseif previous_unassigned_first == previous_unassigned_last then
			left_unassigned_text = ('[sin asignar: U+%.4X]'):format(previous_unassigned_first)
		end

		if next_unassigned_first < next_unassigned_last then
			right_unassigned_text = ('[sin asignar: U+%.4X–U+%.4X]'):format(next_unassigned_first, next_unassigned_last)
		elseif next_unassigned_first == next_unassigned_last then
			right_unassigned_text = ('[sin asignar: U+%.4X]'):format(next_unassigned_first)
		end
	end

	local unassignedsRow =
		mw.html.create('table'):css('width', '100%'):css('font-size', '80%'):css('white-space', 'nowrap')
			:tag('tr')
				:tag('td'):css('width', '50%'):css('text-align', 'left'):wikitext(left_unassigned_text or ''):done()
				:tag('td'):css('width', '50%'):css('text-align', 'right'):wikitext(right_unassigned_text or ''):done()
			:allDone()
	insert(table_markup, tostring(unassignedsRow) ..'\n')

	local previous_codepoint_text = ""
	local next_codepoint_text = ('%s\n'):format(present_codepoint(next_codepoint, true))

	if previous_codepoint > 0 then
		previous_codepoint_text = ('%s\n'):format(present_codepoint(previous_codepoint, false))
	end

	local block_name_text = ('[[Apéndice:Caracteres Unicode/%s|%s]]'):format(block_name, block_name)

	local lastRow =
		mw.html.create('table'):css('width', '100%'):css('text-align', 'center')
			:tag('tr')
				:tag('td'):css('width', '20%'):wikitext(previous_codepoint_text):done()
				:tag('td'):css('width', '60%'):css('font-size', '110%'):css('font-weight', 'bold'):wikitext(block_name_text)
				:tag('td'):css('width', '20%'):wikitext(next_codepoint_text):done()
			:allDone()

	insert(table_markup, tostring(lastRow) ..'\n')

	insert(table_markup, '|}')

	if cat_name and ns == 0 then
		--insert(table_markup, "[[Categoría:" .. cat_name .. "| " .. u(codepoint) .. "]]")
	end

	return concat(table_markup)
end

function export.show(frame)
	local title = mw.title.getCurrentTitle().fullText
	local ns = mw.title.getCurrentTitle().namespace
    if ns ~= 0 then
    	return "Use esta plantilla en el espacio principal."
    end

	local params = {
		[1] = {alias_de = "c"},
		["c"] = {lista = true},
		["mdc"] = {lista = true},
		["egpz"] = {lista = true},
		["gardiner"] = {lista = true},
	}
	local args = require("Módulo:parámetros").obtener_parametros(frame:getParent().args, params)

	local t1 = _show(title, ns, frame, args.c[1], args.mdc[1], args.egpz[1], args.gardiner[1])
	if not args.c[2] then
		return t1
	end

	local t2 = {}
	insert(t2, '{| class="wikitable mostrar-unicode mw-collapsible mw-collapsed"\n')
	insert(t2, '! Otras variantes\n|-\n|')

	for i=2,#args.c do
		insert(t2, _show(title, ns, frame, args.c[i], args.mdc[i], args.egpz[i], args.gardiner[i]))
	end

	insert(t2, "\n|}")
	return t1.."\n"..concat(t2)
end

return export