Moduł:Mapa


Moduł:Mapa w encyklopedii

Z Wikipedii, wolnej encyklopedii Przejdź do nawigacji Przejdź do wyszukiwania  Dokumentacja modułu zobacz historia odśwież

Moduł techniczny do obsługi map lokalizacyjnych.

Spis treści

Wartośćedytuj kod

Funkcja do odczytania parametru z definicji mapy.

parametryedytuj kod

przykładedytuj kod

{{#invoke:Mapa|Wartość|Polska|mapa|fizyczna}} → Relief Map of Poland.svg

Infoboxedytuj kod

Funkcja implementująca {{Infobox mapa lokalizacyjna}}.

Thumbedytuj kod

Funkcja implementująca {{Mapa lokalizacyjna|rodzaj=thumb}}.

Inlineedytuj kod

Funkcja implementująca {{Mapa lokalizacyjna|rodzaj=inline}}.

Błędyedytuj kod

Błędy należy zgłaszać na stronie Wikipedia:Kawiarenka/Kwestie techniczne lub Dyskusja wikiprojektu:Szablony lokalizacyjne.

Zobacz teżedytuj kod

local function getMapParams(map, frame)  mw.logObject(map, "map")  if not map or (#map == 0) then  mw.log("Brak nazwy mapy lokalizacyjnej")  end  local moduleprefix = "Module:Mapa/dane/"  if map then  local moduletitle = mw.title.new(map)  if not moduletitle or (moduletitle.namespace ~= 828) then  moduletitle = mw.title.new(moduleprefix..map)  end  if not moduletitle then  mw.log("„"..map.."” nie jest prawidłową nazwą definicji mapy lokalizacyjnej")  elseif moduletitle.exists then  local status, mapData = pcall(mw.loadData, moduletitle.fullText)  if status then  return function(name, variant)  if name == nil then  --mw.logObject(moduletitle.fullText, "GET module title")  return moduletitle.fullText  end   local variants = variant and mw.text.split(variant, "%s*#%s*") or {}  --mw.logObject(variants, "GET map variants")   if name == true then  for _, v in ipairs(variants) do  --mw.logObject(mapData[v], "GET map variant")  if type(mapData[v]) == "table" then  return v  end  end   return 1  end   for _, v in ipairs(variants) do  if mapData[v] and mapData[v][name] ~= nil then  --mw.logObject({variant=v, name=name, result=mapData[v][name] }, "GET")  return mapData[v][name]  end  end   if mapData[1][name] ~= nil then  --mw.logObject({name=name, result=mapData[1][name] }, "GET")  return mapData[1][name]  end   --mw.logObject({name=name}, "GET")  return ""  end  end  else  mw.log("Nie mogę znaleźć definicji podanej mapy lokalizacyjnej. Nie istnieje „"..moduleprefix..map.."”.")  end  end   -- default fallback  local mapData = mw.loadData(moduleprefix.."brak")  return function(name, variant)  if name == nil then  return false  elseif name == false then  return (map and (#map > 0)) and map or false  elseif name == true then  return 1  elseif mapData[1][name] == nil then  return ""  elseif variant and mapData[variant] then  return mapData[variant][name] or mapData[1][name]  else  return mapData[1][name]  end  end end  local function getX(longitude, left, right)  local width = (right - left) % 360  if width == 0 then  width = 360  end  local distanceFromLeft = (longitude - left) % 360  -- the distance needed past the map to the right equals distanceFromLeft - width. the distance needed past the map to the left equals 360 - distanceFromLeft. to minimize page stretching, go whichever way is shorter  if distanceFromLeft - width / 2 >= 180 then  distanceFromLeft = distanceFromLeft - 360  end  return 100 * distanceFromLeft / width end  local function getY(latitude, top, bottom)  return 100 * (top - latitude) / (top - bottom) end  local function formatCoordinates(parameters)  if not parameters.coordinates then  return false  end   local placement = parameters.placement  if not placement then  placement = ((parameters.linkFlag == false) or (mw.title.getCurrentTitle().namespace ~= 0)) and "w tekście" or "w tekście i na górze"  end   return require("Moduł:Współrzędne")["współrzędne"]({  parameters.coordinates,  parameters.geohack,  ["umieść"] = placement,  ["dokładność"] = parameters.precision,  ["linkuj"] = parameters.linkFlag == false and "nie" or "tak",  symbol = parameters.symbol,  }) end  local function loadMap(frame, map, variant)  local getMapParam = getMapParams(map, frame)  return function(param)  return getMapParam(param, variant)  end end  local function decodePoints(pointsData)  if pointsData and (#pointsData > 0) then  local data = mw.text.jsonDecode("["..pointsData.."{\"dummy\":false}]")  table.remove(data) -- remove last dummy  return data  end end  local function estimateTextWidth(wikicode, fontSize)  local text = mw.ustring.gsub(wikicode, "%[%[[^\n|%]%[]+|([^\n|%]%[]+)%]%]", "%1")  text = mw.ustring.gsub(text, "%[%[([^\n|%]%[]+)%]%]", "%1")  text = mw.ustring.gsub(text, "<[^>]*>", "")  return mw.ustring.len(text) * fontSize end  local function drawMap(builder, get, width, fontSize, data)  local reliefImage = mw.text.trim(get("mapa"))  local reliefTitle = mw.title.new("Plik:"..reliefImage)  if not reliefTitle.file.exists then  reliefTitle = mw.title.new("Plik:Image of nothing.svg")  end  local file = reliefTitle.file  local height = file.height * width / file.width   -- przeliczanie punktów na mapie  local inside = {}  local outside = {}  local errors = {}  local hoverPoints = false  if data and (#data > 0) then  local x_func = mw.text.trim(get("x"))  local y_func = mw.text.trim(get("y"))  local top = get("top")  local left = get("left")  local bottom = get("bottom")  local right = get("right")  if #x_func == 0 then  x_func = false  end  if #y_func == 0 then  y_func = false  end  for i, v in ipairs(data) do  if v.latitude and v.longitude and v.mark and v.size then  -- przeliczanie współrzędnych na pozycje rysowania  if x_func then  local expx = mw.ustring.gsub(mw.ustring.gsub(x_func, "{{{szerokość}}}", v.latitude), "{{{długość}}}", v.longitude)  v.x = tonumber(mw.ext.ParserFunctions.expr(expx))  else  v.x = getX(v.longitude, left, right)  end  if y_func then  local expy = mw.ustring.gsub(mw.ustring.gsub(y_func, "{{{szerokość}}}", v.latitude), "{{{długość}}}", v.longitude)  v.y = tonumber(mw.ext.ParserFunctions.expr(expy))  else  v.y = getY(v.latitude, top, bottom)  end   v.rx = width * v.x / 100  v.ry = height * v.y / 100  if (v.x < 0) or (v.x > 100) or (v.y < 0) or (v.y > 100) then  table.insert(outside, v)  else  table.insert(inside, v)  if not hoverPoints and (v.position == "hover") and v.description then  hoverPoints = true  end  end  elseif v.error then  table.insert(errors, v)  else  -- TODO illegal data or "dummy: false"  mw.logObject(v, "illegal at "..tostring(i))  end  end  end   -- automatyczne pozycjonowanie dwóch punktów  if (#inside == 2) and inside[1].description and inside[2].description and not inside[1].position and not inside[2].position then  local y1 = inside[1].ry  local y2 = inside[2].ry  if (math.abs(y1 - y2) < 16) and (y1 > 8) and (y2 > 8) and ((height - y1) > 8) and ((height - y2) > 8) and (math.abs(inside[1].rx - inside[2].rx) < 80) then  inside[1].position = y2 > y1 and "top" or "bottom"  inside[2].position = y1 > y2 and "top" or "bottom"  end  end   -- tło mapy  local relief = builder:tag("div")  relief:css({ position = "relative", border = "0 solid #aaa", padding = "0", width = tostring(width).."px" })  relief:wikitext("[[Plik:", reliefImage, "|", width, "px|link=")  if not hoverPoints then  local reliefInfo = get("dopełniacz")  if reliefInfo then  relief:wikitext("|Mapa lokalizacyjna ", reliefInfo)  end  end   relief:wikitext("]]")   function showError(category, ...)  local catLink = ""  local known = {  ["brak mapy"] = { "'''Brak mapy:''' ''%s''", "[[Kategoria:Szablony lokalizacyjne - brak mapy]]", },  ["brak kodu mapy"] = { "'''Brak kodu mapy'''", "[[Kategoria:Szablony lokalizacyjne - brak kodu mapy]]", },  ["współrzędne spoza mapy"] = { "'''Współrzędne spoza mapy:''' ''%f %f''", "[[Kategoria:Szablony lokalizacyjne - współrzędne spoza mapy]]", },  ["brak współrzędnych"] = { "'''Brak współrzędnych'''", "[[Kategoria:Szablony lokalizacyjne – brak współrzędnych]]", },  [true] = { "%s", false },  [false] = { "'''''Inny błąd'''''", false, },  }  local k = known[category] or known[false]  local message = mw.ustring.format(k[1], ...)  if k[2] and (mw.title.getCurrentTitle().namespace == 0) then  message = message..k[2]  end  local absolute = relief:tag("div")  :css( { position = "absolute", ["z-index"] = 200, top = "50%", left = "50%", height = 0, width = 0, margin = 0, padding = 0, } )  local msg = absolute:tag("div")  :css( { ["font-size"] = "90%", ["line-height"] = "110%", position = "relative", width = "16em", ["z-index"] = 202, top = "-0.5em", left = "-8em", float = "center", ["text-align"] = "center", background = "white", color = "red", } )  :wikitext(message)  end   -- brak mapy  if not get() then  local map = get(false)  showError(map and "brak mapy" or "brak kodu mapy", map)  if (#inside == 1) and (#outside == 0) then  local v = inside[1]  if (v.longitude == 0) and (v.latitude == 0) then  --mw.log("dummy (0 0) bez mapy nie jest rysowany")  return  end  end  end   -- błędy  if (#inside == 0) and (#outside == 0) then  showError("brak współrzędnych")  end   for i, v in ipairs(outside) do  showError("współrzędne spoza mapy", v.latitude, v.longitude)  end   for i, v in ipairs(errors) do  showError(true, v.error or "?")  end   -- punkty na mapie  for i, v in ipairs(inside) do  local hsize = tostring(v.size/2).."px"  local size = tostring(v.size).."px"  local absolute = relief:tag("div")  :css( { position = "absolute", ["z-index"] = 2, top = tostring(v.y).."%", left = tostring(v.x).."%", height = 0, width = 0, margin = 0, padding = 0, } )  local file = absolute:tag("div")  :css( { position = "relative", ["text-align"] = "center", left = "-"..hsize, top = "-"..hsize, width = size, ["font-size"] = size, ["line-height"] = size, } )  file:wikitext("[[Plik:", v.mark, "|", v.size, "x", size, "|link=", v.link)  if v.description then  file:wikitext("|", v.description)  end  file:wikitext("]]")  -- TODO description  if v.description and (v.position ~= "hover") then   function descriptionWidth(availableWidth)  return availableWidth <= 0 and "auto" or (math.min(availableWidth, 120).."px")  end   local descw = "auto"  local css = {}  if v.position == "right" then  descw = descriptionWidth(math.floor(width - v.rx - (v.size / 2) - 5))  css = { top = "-0.5em", left = tostring((v.size / 2) + 2).."px", ["text-align"] = "left", float = "left" }  elseif v.position == "left" then  descw = descriptionWidth(math.floor(v.rx - (v.size / 2) - 5))  css = { top = "-0.5em", right = tostring((v.size / 2) + 2).."px", ["text-align"] = "right", float = "right" }  elseif v.position == "top" then  descw = "10em"  css = { bottom = tostring((v.size / 4) + 2).."px", left = "-5em", ["text-align"] = "center", float = "center" }  elseif v.position == "bottom" then  descw = "10em"  css = { top = tostring((v.size / 4) + 2).."px", left = "-5em", ["text-align"] = "center", float = "center" }  else -- auto  local textWidth = estimateTextWidth(v.description, fontSize) * 0.6  if (v.x < 50) or ((v.rx + textWidth + (v.size / 2) + 2) < width) then -- right  descw = descriptionWidth(math.floor(width - v.rx - (v.size / 2) - 5))  css = { top = "-0.5em", left = tostring((v.size / 2) + 2).."px", ["text-align"] = "left", float = "left" }  elseif ((v.rx - (v.size / 2) - 2) > textWidth) or (v.x > 70) then -- left  descw = descriptionWidth(math.floor(v.rx - (v.size / 2) - 5))  css = { top = "-0.5em", right = tostring((v.size / 2) + 2).."px", ["text-align"] = "right", float = "right" }  elseif (v.y > 50) then -- top  descw = "10em"  css = { bottom = tostring((v.size / 4) + 2).."px", left = "-5em", ["text-align"] = "center", float = "center" }  else -- bottom  descw = "10em"  css = { top = tostring((v.size / 4) + 2).."px", left = "-5em", ["text-align"] = "center", float = "center" }  end  end   local desc = absolute:tag("div")  :css( { ["font-size"] = tostring(fontSize).."px", ["line-height"] = tostring(1.2*fontSize).."px", ["z-index"] = "90", ["position"] = "absolute", ["width"] = descw, } )  desc:css(css)  desc:tag("span")  :css({ padding = "1px", ["text-shadow"] = "0 0 5px white;" })  :wikitext(v.description)  end  end end  local function makeTrackingLinks(get, group)  local linkAlias = get("link alias")  local mapVariant = get(true)  if not linkAlias or (#linkAlias == 0) then  return  end   local trackingLink = "Moduł:Mapa/linkujące/"..linkAlias.."/"..group  _ = mw.title.new(trackingLink).id  _ = mw.title.new(trackingLink.."/"..mapVariant).id end  local function adjustPointParams(points, mapgeohack)  for i, p in ipairs(points) do  local link = p.link  if link then  if mapgeohack==false then  p.link = ""  elseif mapgeohack then  p.link = link.."_"..mapgeohack  elseif p.geohack then  p.link = link.."_"..p.geohack  end  end  end end  return {   ["Wartość"] = function(frame)  local f = frame.args[1] and frame or frame:getParent()  return getMapParams(f.args[1], frame)(f.args[2], f.args[3])  end,   ["Infobox"] = function(frame)  -- log wskazujący na początek wywołania funkcji  mw.log("{{#invoke:Moduł:Mapa|Infobox}}")  local args = require('Module:Arguments').getArgs(frame, {  trim = true,  removeBlanks = true,  wrappers = "Szablon:Infobox mapa lokalizacyjna",  })  local defaultIcon = "[[Plik:Geographylogo.svg|20px|alt=Ziemia|link=Ziemia]]"  local map = args["mapa"] or "brak"  local variant = args["wariant"]  local description = args["opis"]  local mark = args["znak na mapie"] or "Red pog.svg"  local markSize = tonumber(args["wielkość znaku"]) or 6  local coordinates = args["współrzędne"]  if not coordinates then  mw.log("infobox może wyszukać współrzędne w wikidanych")  else  mw.log("współrzędne: "..coordinates)  end  local precision = args["dokładność"]  local twoMaps = args["dwie mapy"]  local category = args["kategoria"]  local geohack = args["opcje geohack"]  local position = args["pozycja opisu"]  local points = args["punkty mapy"]  mw.logObject({precision = precision, twoMaps = twoMaps, category = category, geohack = geohack, position = position, points = points}, "argumenty")  if points and not string.match(points, "%s*{") then  mw.log("załączone punkty do mapy są w nieodpowiednim formacie")  return  end  if not points and not coordinates then  if args["wikidane"] == "nie" then  mw.log("brak punktów na mapę, a nie ma pozwolenia na Wikidane")  elseif map ~= "pusta" then  mw.log("brak punktów na mapę i współrzędnych, nadszedł czas na Wikidane")  local display = true  if (map ~= "osobna") and (map ~= "niedostępna") then  display = "#coordinates"  end  local p = require("Moduł:Współrzędne").punkt({  ["opcje geohack"] = geohack,  ["znak"] = mark,  ["rozmiar znaku"] = markSize,  ["opis"] = description,  ["pozycja"] = position,  ["dokładność"] = precision,  display = display,  symbol = false,  })  if not p then  mw.log("brak punktów na mapę nawet w Wikidanych")  end   points = p  end  end  if not points and not coordinates and (mw.title.getCurrentTitle().fullText == frame:getParent():getTitle()) and (type(frame.getParent) == "function") then  --TEST ANY ARG  local any = false  for k, v in pairs(frame:getParent().args) do  any = true  break  end   if not any then  -- brak jakichkolwiek argumentów w szablonie to tryb demo  points = require("Moduł:Współrzędne").punkt({ "0 0", display = true, symbol = false, })  map = "brak"  end  end  if not points and not coordinates then  if not category or (mw.title.getCurrentTitle().namespace ~= 0) or (map == "żadna") or (map == "osobna") or (map == "pusta") or (map == "niedostępna") then  return  end   return '|- style="display:none;"\n!colspan="2"|brak współrzędnych[[Kategoria:Szablony lokalizacyjne – brak współrzędnych – '..category..']]\n|-'  end   local result = {}  local coords = false  if (map == "żadna") or (map == "none") then  _ = mw.title.new("Moduł:Mapa/linkujące/żadna").id  -- TODO współrzędne, geohack, linkuj=tak, dokładność=kątowo, umieść=w tekście (i na górze)  coords = formatCoordinates({  coordinates = coordinates,  geohack = geohack,  linkFlag = true,  })  elseif map == "osobna" then  _ = mw.title.new("Moduł:Mapa/linkujące/osobna").id  -- TODO współrzędne, geohack, linkuj=tak, dokładność=kątowo, umieść=w tekście  coords = formatCoordinates({  coordinates = coordinates,  geohack = geohack,  linkFlag = true,  placement = "w tekście",  })  elseif map == "pusta" then  _ = mw.title.new("Moduł:Mapa/linkujące/pusta").id  -- no map nor coordinates  elseif map == "niedostępna" then  _ = mw.title.new("Moduł:Mapa/linkujące/niedostępna").id  -- TODO współrzędne, globe:none, linkuj=nie, dokładność=dziesiętnie, normalizacja=auto, ikona=  coords = formatCoordinates({  coordinates = coordinates,  linkFlag = false,  precision = precision or "dziesiętnie",  })  else  local maps = {}  local list = string.match(map, "#")  for v in mw.ustring.gmatch(map, "[^#]+") do  table.insert(maps, mw.text.trim(v))  end  if #maps == 0 then  table.insert(maps, map)  end  if not list and (twoMaps ~= "nie") then  while #map > 0 do  local get = loadMap(frame, map, variant)  map = mw.text.trim(get("nadrzędna") or "")  if #map > 0 then  table.insert(maps, 2, map)  end  end  end   local mapIndex = 1  local map = maps[mapIndex]  local get = loadMap(frame, map, variant)  -- prepare coordinates under the map  local icon = mw.text.trim(get("ikona") or "")  if #icon == 0 then  icon = defaultIcon  end   local mapPrecision = get("dokładność")  if mapPrecision and (#mapPrecision <= 0) then  mapPrecision = nil  end   coords = formatCoordinates({  coordinates = coordinates,  geohack = geohack or get("globe") or "",  linkFlag = get("globe") ~= false,  precision = precision or mapPrecision or "kątowo",  symbol = icon,  })   if coordinates then  local p = require("Moduł:Współrzędne").punkt({  coordinates,  ["opcje geohack"] = geohack,  ["znak"] = mark,  ["rozmiar znaku"] = markSize,  ["opis"] = description,  ["pozycja"] = position,  symbol = false,  })  points = points and (p..points) or p  end   local pointsData = decodePoints(points)  if pointsData then  adjustPointParams(pointsData, get("globe"))  end   if not coords and pointsData and (#pointsData > 0) then  icon = false  coords = pointsData[1].display  end   -- tracking link, pseudo reference to primary map  makeTrackingLinks(get, "primary")   -- draw maps  while map do  map = nil  -- draw map  local mapWidth = tonumber(get("rozmiar")) or 238  if mapWidth > 238 then  mapWidth = 238  elseif mapWidth < 100 then  mapWidth = 100  end  local map1 = mw.html.create("div")  :css( { margin="0 auto", ["text-align"]="center", width=tostring(mapWidth+4).."px" } )  map1:tag("div")  :css( { ["font-weight"]= "bold", color="gray" } )  :wikitext("Położenie na mapie ", get("dopełniacz"))  drawMap(map1:tag("div"):addClass("mapa-lokalizacyjna"), get, mapWidth, 12.6, pointsData)  table.insert(result, '|- class="infobox-locationmap" style="background-color:white; text-align:center; border-top:1px solid #aaa;"\n|colspan="2"|')  table.insert(result, tostring(map1:allDone()))  table.insert(result, "\n")  -- next parent  if mapIndex < #maps then  mapIndex = mapIndex + 1  map = maps[mapIndex]  get = loadMap(frame, map, variant)  end  end  end   if coords then  table.insert(result, '|-\n|colspan="2" style="background-color:white; text-align:center; border-bottom:1px solid #aaa;"|')  table.insert(result, coords)  table.insert(result, "\n")  end   if #result > 0 then  table.insert(result, "|-")  end   return table.concat(result)  end,   ["Thumb"] = function(frame)  local args = require('Module:Arguments').getArgs(frame, {  trim = true,  removeBlanks = false,  wrappers = "Szablon:Mapa lokalizacyjna",  })  local map = args["mapa"] or args[1] or "{{{1}}}"  if #map == 0 then  map = nil  end  local variant = args["wariant"]  local width = tonumber(args["rozmiar"]) or 238  local fontSize = tonumber(args["font-size"]) or 12.6  local align = args["wyrównanie"] or "right"  local footer = args["podpis"]  local pointsData = decodePoints(args["punkty mapy"])   local get = loadMap(frame, map, variant)  if pointsData then  adjustPointParams(pointsData, get("globe"))  end   -- tracking link, pseudo reference to this map  makeTrackingLinks(get, "standalone")   local positionClass = {  ["center"] = "center",  ["right"] = "tright",  ["left"] = "tleft",  [""] = "tnone",  }  local thumb = mw.html.create("div")  :addClass("thumb")  :addClass(positionClass[align] or align)  :addClass("panel-with-scroll")  :wikitext('\n')  local thumbinner = thumb:tag("div")  :addClass("thumbinner")  :css({ width = tostring(width + 2).."px" })  :wikitext('\n')  local border = thumbinner:tag("div")  :css({ border = "1px solid #ccc", width = tostring(width).."px !important" })  local builder = border:tag("div")  --:addClass("mapa-lokalizacyjna")  :css({ margin = "0 auto", width = tostring(width).."px" })  drawMap(builder, get, width, fontSize, pointsData)  if pointsData and (#pointsData == 1) and (mw.title.getCurrentTitle().namespace == 0) then  builder:wikitext("[[Kategoria:Mapa lokalizacyjna z jednym punktem]]")  end  thumbinner  :wikitext('\n')  local thumbcaption = thumbinner:tag("div")  :addClass("thumbcaption")  thumbcaption:tag("div")  :addClass("magnify")  :wikitext("[[Plik:Geographylogo.svg|16x16px|link=Wikiprojekt:Szablony lokalizacyjne]]")  if footer and (#footer > 0) then  thumbcaption:wikitext(footer)  else  thumbcaption:wikitext("Położenie na mapie ", mw.text.nowiki(get("dopełniacz") or ""))  end  thumbinner  :wikitext('\n')  thumb  :wikitext('\n')  return thumb:allDone()  end,   ["Inline"] = function(frame)  local args = require('Module:Arguments').getArgs(frame, {  trim = true,  removeBlanks = false,  wrappers = "Szablon:Mapa lokalizacyjna",  })  local map = args["mapa"] or args[1] or "{{{1}}}"  if #map == 0 then  map = nil  end  local variant = args["wariant"]  local width = tonumber(args["rozmiar"]) or 238  local fontSize = tonumber(args["font-size"]) or 12.6  local pointsData = decodePoints(args["punkty mapy"])   local get = loadMap(frame, map, variant)  if pointsData then  adjustPointParams(pointsData, get("globe"))  end   -- tracking link, pseudo reference to this map  makeTrackingLinks(get, "standalone")   local builder = mw.html.create("div")  :addClass("mapa-lokalizacyjna")  :css({ margin ="0 auto", width = tostring(width + 2).."px", padding = "3px", margin = "3px" })  drawMap(builder, get, width, fontSize, pointsData)  if pointsData and (#pointsData == 1) and (mw.title.getCurrentTitle().namespace == 0) then  builder:wikitext("[[Kategoria:Mapa lokalizacyjna z jednym punktem]]")  end  return builder:allDone()  end,  } 
Na podstawie artykułu: "Moduł:Mapa" pochodzącego z Wikipedii
OryginałEdytujHistoria i autorzy