Zum Inhalt springen


Modul:Link: Unterschied zwischen den Versionen

Aus Firestone Idle RPG Wiki
Die Seite wurde neu angelegt: „-- Modul:Link local p = {} -- Tooltip-Daten (read-only, performant) local data = mw.loadData('Modul:LinkData') -- Merker, welche <ref name="…"> durch DIESES Modul -- in dieser Seiten-Expansion bereits definiert wurden local defined = {} local function trim(s) if type(s) ~= 'string' then return '' end return (s:gsub('^%s+', ''):gsub('%s+$', '')) end local function yes(v) if v == nil then return false end if type(v) == 'boolean' then return v…“
 
Keine Bearbeitungszusammenfassung
Zeile 1: Zeile 1:
-- Modul:Link
-- Modul:ToolTip
local p = {}
local p = {}


-- Tooltip-Daten (read-only, performant)
local data = mw.loadData('Modul:ToolTipData')
local data = mw.loadData('Modul:LinkData')
local US = mw.ustring
 
local DEFAULT_LIMIT = 220
-- Merker, welche <ref name="…"> durch DIESES Modul
-- in dieser Seiten-Expansion bereits definiert wurden
local defined = {}


local function trim(s)
local function trim(s)
   if type(s) ~= 'string' then return '' end
   if type(s) ~= 'string' then return '' end
   return (s:gsub('^%s+', ''):gsub('%s+$', ''))
   return (s:gsub('^%s+',''):gsub('%s+$',''))
end
 
local function yes(v)
  if v == nil then return false end
  if type(v) == 'boolean' then return v end
  v = tostring(v):lower()
  return v == '1' or v == 'y' or v == 'yes' or v == 'true' or v == 'ja'
end
end


-- Key-Normalisierung für LinkData: kleinschreiben, Whitespace bündeln
local function normalize_key(s)
local function normalize_key(s)
   s = trim(s or '')
   s = trim(s or '')
   if s == '' then return s end
   s = US.lower(s)
  s = mw.ustring.lower(s)
   s = s:gsub('_',' '):gsub('%s+',' ')
  -- Unterstriche und Mehrfach-Spaces vereinheitlichen
   s = s:gsub('_', ' '):gsub('%s+', ' ')
   return s
   return s
end
end


local function strip_wrapping_quotes(s)
-- Links im Wikitext zu neutralem Text machen (für Tooltip)
   s = trim(s or '')
local function strip_links(txt)
   if mw.ustring.match(s, '^".*"$') then
  txt = txt or ''
     return mw.ustring.sub(s, 2, -2)
 
  -- [[Ziel|Text]] -> Text
  txt = txt:gsub('%[%[([^%]|%]]-)|([^\]]-)%]%]', '%2')
 
  -- [[Ziel]] -> Ziel (ohne Namespace/Unterstriche grob beibehalten)
  txt = txt:gsub('%[%[([^%]]-)%]%]', function(inner)
    return inner:gsub('_',' ')
  end)
 
  -- [http(s)://url Label] -> Label
  txt = txt:gsub('%[(https?://[^%s%]]+)%s+([^\]]-)%]', '%2')
 
   -- [http(s)://url] -> url
  txt = txt:gsub('%[(https?://[^%]]+)%]', '%1')
 
  return txt
end
 
local function shorten(txt, limit)
  limit = tonumber(limit) or DEFAULT_LIMIT
  local len = US.len(txt or '')
   if len <= limit then return txt end
  local cut = US.sub(txt, 1, limit)
  local lastSpace = cut:match('^.*()%s')
  if lastSpace and lastSpace > 15 then
     cut = US.sub(cut, 1, lastSpace - 1)
   end
   end
   return s
   return cut .. '…'
end
 
local function htmlize_plain(txt)
  txt = tostring(txt or '')
  txt = mw.text.encode(txt)          -- HTML-sicher
  txt = txt:gsub('\n','<br/>')
  return txt
end
end


local function build_link(target, display)
local function make_link(target, display)
   target  = trim(target)
   target  = trim(target)
   display = display and tostring(display) or nil
   display = display and trim(display) or ''
   if display and trim(display) ~= '' then
   if display ~= '' then
    -- Anzeige GENAU so ausgeben, wie übergeben
     return '[[' .. target .. '|' .. display .. ']]'
     return '[[' .. target .. '|' .. display .. ']]', display
   else
   else
     return '[[' .. target .. ']]', nil
     return '[[' .. target .. ']]'
   end
   end
end
end


local function tooltip_wrap(link_html, key_norm)
local function render_hover(link_wikitext, info, limit)
   -- Daten lookup (erst "a b", dann "a_b" als Fallback)
   if not info or (not info.title and not info.desc and not info.icon) then
   local info = data[key_norm] or data[key_norm:gsub(' ', '_')] or {}
    return link_wikitext -- keine Daten -> normaler Link
   end


   -- Fallback-Titel: normalisierter Key (erste Silbe groß kannst du im Data steuern)
   local wrap   = mw.html.create('span'):addClass('kr-tt')
   local title = info.title or key_norm
   wrap:wikitext(link_wikitext)
  local desc  = info.desc or ''
   local icon  = info.icon or ''


  -- Wenn gar nichts hinterlegt ist, trotzdem einen Tooltip zeigen (mit einfachem Titel)
   local content = mw.html.create('span'):addClass('kr-tt__content')
   local box = mw.html.create('span'):addClass('kr-tt__content')
   local box    = mw.html.create('span'):addClass('kr-tt__box')
   local inner = mw.html.create('span'):addClass('kr-tt__box')


   if icon ~= '' then
   if info.icon and info.icon ~= '' then
     inner:wikitext('[[File:' .. icon .. '|28x28px|link=|class=kr-tt__icon]]')
     box:wikitext('[[File:' .. info.icon .. '|28x28px|link=|class=kr-tt__icon]]')
   else
   else
     inner:wikitext('<span class="kr-tt__icon kr-tt__icon--empty"></span>')
     box:wikitext('<span class="kr-tt__icon kr-tt__icon--empty"></span>')
   end
   end


   local text = mw.html.create('span'):addClass('kr-tt__text')
   local text = mw.html.create('span'):addClass('kr-tt__text')
   text:tag('span'):addClass('kr-tt__title'):wikitext(title)
   local title = info.title or ''
   if desc ~= '' then
   local desc = info.desc  or ''
    text:tag('span'):addClass('kr-tt__desc'):wikitext(desc)
 
  end
  desc = strip_links(desc)
  desc = shorten(desc, limit)


   inner:node(text)
   text:tag('span'):addClass('kr-tt__title'):wikitext(htmlize_plain(title))
   box:node(inner)
   text:tag('span'):addClass('kr-tt__desc'):wikitext(htmlize_plain(desc))


   local wrap = mw.html.create('span'):addClass('kr-tt')
   box:node(text)
   wrap:wikitext(link_html)
   content:node(box)
   wrap:node(box)
   wrap:node(content)
   return tostring(wrap)
   return tostring(wrap)
end
local function render_view(info)
  -- große Box wie im Screenshot (volle Beschreibung inkl. klickbarer Links)
  local title = info and info.title or ''
  local desc  = info and info.desc  or ''
  local icon  = info and info.icon  or ''
  local tbl = mw.html.create('table'):addClass('kr-tt-view')
  local trh = tbl:tag('tr')
  trh:tag('th'):attr('colspan','2'):wikitext(title ~= '' and title or '&nbsp;')
  local tr = tbl:tag('tr')
  local tdIcon = tr:tag('td'):addClass('kr-tt-view__icon')
  if icon ~= '' then
    tdIcon:wikitext('[[File:' .. icon .. '|64x64px|class=kr-tt-view__iconimg|link=]]')
  else
    tdIcon:wikitext('&nbsp;')
  end
  tr:tag('td'):addClass('kr-tt-view__desc'):wikitext(desc or '')
  return tostring(tbl)
end
end


Zeile 88: Zeile 127:
   local args = parent and parent.args or frame.args
   local args = parent and parent.args or frame.args


  -- Params
   local target = trim(args[1] or '')
   local target   = trim(args[1] or args.target or '')
   if target == '' then return '' end
  local display  = args[2] or args.display
  local key      = args.key  -- optional: expliziter Tooltip-Key (beliebige Schreibweise)
  local refText  = args.ref
  local refName  = args.name or args.refname
  local hasRef  = args.has_refname
  local tooltip  = yes(args.tooltip)
                    or (type(args[2]) == 'string' and args[2]:lower() == 'tooltip')
                    or (type(args[3]) == 'string' and args[3]:lower() == 'tooltip')
                    or (type(args[4]) == 'string' and args[4]:lower() == 'tooltip')
 
   if target == '' then
    return ''
  end


   -- Link bauen (Anzeige UNVERÄNDERT)
   local p2 = args[2] and trim(args[2]) or ''
   local link, shownText = build_link(target, display)
   local mode_view = (US.lower(p2) == 'view')


   -- Tooltip-Key ableiten und normalisieren
   -- Key bestimmen: bei [[URL|Anzeigename]] ist 2. Param der Anzeigename,
   if not key or trim(key) == '' then
  -- sonst nehmen wir den 1. Param. Explizit überschreibbar via |key=
    if shownText and trim(shownText) ~= '' then
   local key = trim(args.key or (mode_view and target or (p2 ~= '' and p2 or target)))
      key = shownText
   local key_norm = normalize_key(key)
    elseif target:find('#', 1, true) then
      key = target:match('#(.+)$') or target
    else
      key = target
    end
  end
   local key_norm = normalize_key((key:gsub('^.+#', '')):gsub('%[.+%]', ''))


   -- Tooltip ggf. anwenden
   local info = data[key_norm] or data[key_norm:gsub(' ','_')] or nil
  if tooltip then
   local limit = tonumber(args.limit or '') or DEFAULT_LIMIT
    link = tooltip_wrap(link, key_norm)
   end


  -- Referenzen
   if mode_view then
  local out = link
     return render_view(info or {})
   if refText and trim(refText) ~= '' then
  else
     refText = strip_wrapping_quotes(refText)
     local link_wt = make_link(target, (p2 ~= '' and p2 or nil))
     if refName and trim(refName) ~= '' then
     return render_hover(link_wt, info or {}, limit)
      local safeName = trim(refName):gsub('"', '&quot;')
      out = out .. '<ref name="' .. safeName .. '">' .. refText .. '</ref>'
      defined[safeName] = true
    else
      out = out .. '<ref>' .. refText .. '</ref>'
    end
  elseif hasRef and trim(hasRef) ~= '' then
    local name = trim(hasRef)
     if defined[name] then
      local safeName = name:gsub('"', '&quot;')
      out = out .. '<ref name="' .. safeName .. '" />'
    end
   end
   end
  return out
end
end


return p
return p

Version vom 24. Oktober 2025, 00:14 Uhr

Erzeugt interne Links mit Hover-Tooltip (Icon, Titel, Kurzbeschreibung) aus Modul:LinkData. Optional kann eine „Detailansicht“ (Wikitable) ausgegeben werden.

Grundsyntax

Tooltip-Link
{{Link|Ziel}}
Tooltip-Link mit eigenem Anzeigenamen
{{Link|Ziel|Anzeigename}}
Detailansicht (Tabelle) statt Link
{{Link|Ziel|view}}

Parameter

Param Name Typ/Standard Beschreibung
1 Ziel Pflicht Seitentitel oder „Titel#Abschnitt“. Wird als Linkziel verwendet.
2 Anzeigename / view / Kurz-Suffix optional
  • leer → Anzeigename = title aus LinkData
  • view → gibt die Tabelle aus
  • +… → Kurz-Suffix für Plural etc. (siehe unten)
s s (Suffix) optional Hängt Text an den Anzeigenamen aus LinkData an (z. B. s=e → „Biere“).
key key optional Erzwingt den Datensatz-Schlüssel für LinkData (falls Ziel und title nicht übereinstimmen).
limit limit Zahl (220) Maximale Länge der Tooltip-Beschreibung; bei Überschreitung wird abgeschnitten (…).

Verhalten

Anzeigename

  • Standardmäßig wird als Anzeigename der deutsche Titel aus Modul:LinkData verwendet (Feld title).
  • Eigener Anzeigename (2. Parameter) überschreibt den Titel.
  • Groß-/Kleinschreibung bleibt genau wie im Wikitext/LinkData.

Plural / LinkTrail

MediaWikis LinkTrail funktioniert nur bei direkt geschriebenen Links, nicht bei Vorlagen. Dafür gibt es zwei Wege:

  1. Suffix-Kurzform im 2. Parameter:
{{Link|Bier|+e}}Lua-Fehler in package.lua, Zeile 80: module 'Modul:ToolTipData' not found
{{Link|Bier|+en}}Lua-Fehler in package.lua, Zeile 80: module 'Modul:ToolTipData' not found
  1. Expliziter Suffix über s=:
{{Link|Bier|s=e}}Lua-Fehler in package.lua, Zeile 80: module 'Modul:ToolTipData' not found

Hinweise:

  • Sobald ein eigener Anzeigename gesetzt ist, wird s= ignoriert.
  • Bei „unpiped“ Links (also wirklich Biere) greift LinkTrail – das ist mit Vorlagen technisch nicht möglich. Nutze daher s= / +….

Anker/Abschnitte

  • Bei Zielen mit # (z. B. Währungen#Bier) wird immer ein gepipter Link erzeugt (kein LinkTrail / ToolTip möglich).
  • Die Detailansicht (view) setzt die Tabellen-ID anhand des Titels (Leerzeichen → Unterstrich).

Tooltip

  • Holt title / icon / desc aus Modul:LinkData.
  • Links in der Beschreibung werden im Hover-Tooltip zu normalem Text neutralisiert.
  • Zeilenumbrüche werden unterstützt; lange Texte werden nach limit Zeichen abgeschnitten.

Fallbacks

  • Gibt es keinen Datensatz in LinkData, wird ein normaler Link ohne Tooltip ausgegeben.

Beispiele

Standard
{{Link|Bier}}Lua-Fehler in package.lua, Zeile 80: module 'Modul:ToolTipData' not found
Eigener Anzeigename
{{Link|Währungen#Bier|Bier}}Lua-Fehler in package.lua, Zeile 80: module 'Modul:ToolTipData' not found
Plural via Suffix (Kurzform)
{{Link|Bier|+e}}Lua-Fehler in package.lua, Zeile 80: module 'Modul:ToolTipData' not found
Plural via s=
{{Link|Bier|s=en}}Lua-Fehler in package.lua, Zeile 80: module 'Modul:ToolTipData' not found
Detailansicht (Wikitable)
{{Link|Bier|view}}Lua-Fehler in package.lua, Zeile 80: module 'Modul:ToolTipData' not found
Limit anpassen
{{Link|Bier|limit=50}}Lua-Fehler in package.lua, Zeile 80: module 'Modul:ToolTipData' not found
Abweichender Datensatz (engl. key)
{{Link|Währungen|key=Beer}}Lua-Fehler in package.lua, Zeile 80: module 'Modul:ToolTipData' not found

-- Modul:ToolTip
local p = {}

local data = mw.loadData('Modul:ToolTipData')
local US = mw.ustring
local DEFAULT_LIMIT = 220

local function trim(s)
  if type(s) ~= 'string' then return '' end
  return (s:gsub('^%s+',''):gsub('%s+$',''))
end

local function normalize_key(s)
  s = trim(s or '')
  s = US.lower(s)
  s = s:gsub('_',' '):gsub('%s+',' ')
  return s
end

-- Links im Wikitext zu neutralem Text machen (für Tooltip)
local function strip_links(txt)
  txt = txt or ''

  -- [[Ziel|Text]] -> Text
  txt = txt:gsub('%[%[([^%]|%]]-)|([^\]]-)%]%]', '%2')

  -- [[Ziel]] -> Ziel (ohne Namespace/Unterstriche grob beibehalten)
  txt = txt:gsub('%[%[([^%]]-)%]%]', function(inner)
    return inner:gsub('_',' ')
  end)

  -- [http(s)://url Label] -> Label
  txt = txt:gsub('%[(https?://[^%s%]]+)%s+([^\]]-)%]', '%2')

  -- [http(s)://url] -> url
  txt = txt:gsub('%[(https?://[^%]]+)%]', '%1')

  return txt
end

local function shorten(txt, limit)
  limit = tonumber(limit) or DEFAULT_LIMIT
  local len = US.len(txt or '')
  if len <= limit then return txt end
  local cut = US.sub(txt, 1, limit)
  local lastSpace = cut:match('^.*()%s')
  if lastSpace and lastSpace > 15 then
    cut = US.sub(cut, 1, lastSpace - 1)
  end
  return cut .. '…'
end

local function htmlize_plain(txt)
  txt = tostring(txt or '')
  txt = mw.text.encode(txt)           -- HTML-sicher
  txt = txt:gsub('\n','<br/>')
  return txt
end

local function make_link(target, display)
  target  = trim(target)
  display = display and trim(display) or ''
  if display ~= '' then
    return '[[' .. target .. '|' .. display .. ']]'
  else
    return '[[' .. target .. ']]'
  end
end

local function render_hover(link_wikitext, info, limit)
  if not info or (not info.title and not info.desc and not info.icon) then
    return link_wikitext -- keine Daten -> normaler Link
  end

  local wrap   = mw.html.create('span'):addClass('kr-tt')
  wrap:wikitext(link_wikitext)

  local content = mw.html.create('span'):addClass('kr-tt__content')
  local box     = mw.html.create('span'):addClass('kr-tt__box')

  if info.icon and info.icon ~= '' then
    box:wikitext('[[File:' .. info.icon .. '|28x28px|link=|class=kr-tt__icon]]')
  else
    box:wikitext('<span class="kr-tt__icon kr-tt__icon--empty"></span>')
  end

  local text = mw.html.create('span'):addClass('kr-tt__text')
  local title = info.title or ''
  local desc  = info.desc  or ''

  desc = strip_links(desc)
  desc = shorten(desc, limit)

  text:tag('span'):addClass('kr-tt__title'):wikitext(htmlize_plain(title))
  text:tag('span'):addClass('kr-tt__desc'):wikitext(htmlize_plain(desc))

  box:node(text)
  content:node(box)
  wrap:node(content)
  return tostring(wrap)
end

local function render_view(info)
  -- große Box wie im Screenshot (volle Beschreibung inkl. klickbarer Links)
  local title = info and info.title or ''
  local desc  = info and info.desc  or ''
  local icon  = info and info.icon  or ''

  local tbl = mw.html.create('table'):addClass('kr-tt-view')
  local trh = tbl:tag('tr')
  trh:tag('th'):attr('colspan','2'):wikitext(title ~= '' and title or '&nbsp;')

  local tr = tbl:tag('tr')
  local tdIcon = tr:tag('td'):addClass('kr-tt-view__icon')
  if icon ~= '' then
    tdIcon:wikitext('[[File:' .. icon .. '|64x64px|class=kr-tt-view__iconimg|link=]]')
  else
    tdIcon:wikitext('&nbsp;')
  end
  tr:tag('td'):addClass('kr-tt-view__desc'):wikitext(desc or '')

  return tostring(tbl)
end

function p.main(frame)
  local parent = frame:getParent()
  local args = parent and parent.args or frame.args

  local target = trim(args[1] or '')
  if target == '' then return '' end

  local p2 = args[2] and trim(args[2]) or ''
  local mode_view = (US.lower(p2) == 'view')

  -- Key bestimmen: bei [[URL|Anzeigename]] ist 2. Param der Anzeigename,
  -- sonst nehmen wir den 1. Param. Explizit überschreibbar via |key=
  local key = trim(args.key or (mode_view and target or (p2 ~= '' and p2 or target)))
  local key_norm = normalize_key(key)

  local info = data[key_norm] or data[key_norm:gsub(' ','_')] or nil
  local limit = tonumber(args.limit or '') or DEFAULT_LIMIT

  if mode_view then
    return render_view(info or {})
  else
    local link_wt = make_link(target, (p2 ~= '' and p2 or nil))
    return render_hover(link_wt, info or {}, limit)
  end
end

return p