MediaWiki:Common.js: Unterschied zwischen den Versionen
Admin (Diskussion | Beiträge) Keine Bearbeitungszusammenfassung Markierung: Manuelle Zurücksetzung |
Admin (Diskussion | Beiträge) Keine Bearbeitungszusammenfassung |
||
| Zeile 743: | Zeile 743: | ||
function ensureChartJS(cb){ | function ensureChartJS(cb){ | ||
if (window.Chart) return cb(); | if (window.Chart) return cb(); | ||
| Zeile 752: | Zeile 751: | ||
} | } | ||
// | const ADOS_COLORS = { | ||
'A Dream of Scotland': '#ef4444', // rot | |||
'A Dream of Ireland': '#10b981', // grün | |||
'A Dream of... – Der Rest der Welt': '#8b5cf6', // violett | |||
'Friendly Mr. Z': '#0ea5e9', // blau | |||
'Die Whisky Elfen': '#14b8a6', // türkis | |||
'The Fine Art of Whisky': '#e11d48' // pink-rot | |||
}; | |||
const COLOR_CYCLE = ['#2563eb','#16a34a','#f97316','#dc2626','#a855f7','#0ea5e9','#f59e0b','#10b981']; | |||
function toYear(x){ const n=parseInt(String(x).replace(/[^\d]/g,''),10); return isFinite(n)?n:null; } | |||
function getColor(name, used){ return ADOS_COLORS[name] || COLOR_CYCLE[(used.size)%COLOR_CYCLE.length] && (used.add(name), COLOR_CYCLE[(used.size-1)%COLOR_CYCLE.length]); } | |||
function buildDatasetsFromTable(tbl){ | |||
const rows=[...tbl.querySelectorAll('tr')]; if(rows.length<2) return {labels:[],datasets:[]}; | |||
const years=new Set(), map=new Map(); | |||
rows.slice(1).forEach(tr=>{ | |||
const tds=tr.querySelectorAll('td,th'); if(tds.length<3) return; | |||
const y=toYear(tds[0].textContent), s=tds[1].textContent.trim(), v=parseFloat(tds[2].textContent.replace(',','.'))||0; | |||
if(y==null) return; years.add(y); if(!map.has(s)) map.set(s,new Map()); map.get(s).set(y,v); | |||
}); | |||
const labels=[...years].sort((a,b)=>a-b).map(String); | |||
const used=new Set(); | |||
const datasets=[...map.entries()].map(([name,ym])=>{ | |||
const data=labels.map(y=>ym.get(+y)||0); const c=getColor(name,used); | |||
return { label:name, data, borderColor:c, backgroundColor:c+'80', tension:.25, pointRadius:3 }; | |||
}); | |||
return {labels,datasets}; | |||
} | |||
function renderMultiChart(block){ | |||
let tbl=block.nextElementSibling; while(tbl && tbl.tagName!=='TABLE') tbl=tbl.nextElementSibling; | |||
if(!tbl) return; | |||
const {labels,datasets}=buildDatasetsFromTable(tbl); if(!labels.length||!datasets.length) return; | |||
const wrap=document.createElement('div'); wrap.style.position='relative'; wrap.style.height='440px'; wrap.style.width='100%'; | |||
const canvas=document.createElement('canvas'); wrap.appendChild(canvas); block.innerHTML=''; block.appendChild(wrap); | |||
const type=(block.dataset.type||'line').toLowerCase(); const title=block.dataset.title||''; | |||
new Chart(canvas.getContext('2d'), { | |||
type, data:{labels,datasets}, | |||
options:{ responsive:true, maintainAspectRatio:false, | |||
scales:{ y:{ beginAtZero:true, ticks:{ precision:0 } } }, | |||
plugins:{ legend:{ position:'bottom' }, title:{ display:!!title, text:title } } | |||
} | |||
} | |||
}); | }); | ||
} | } | ||
mw.hook('wikipage.content').add(function($c){ | mw.hook('wikipage.content').add(function($c){ | ||
const scope=($c&&$c[0])?$c[0]:document; | |||
const blocks=scope.querySelectorAll('.ados-chart-multi'); | |||
if(!blocks.length) return; | |||
ensureChartJS(()=>blocks.forEach(renderMultiChart)); | |||
}); | }); | ||