Files
mediabuy-wh/index.html
T
2026-08-25 18:52:39 +08:00

62 lines
5.2 KiB
HTML
Raw Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
<!DOCTYPE html>
<html lang="zh-CN">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>武汉自投 · 投手投放花费报告</title>
<script src="https://cdn.jsdelivr.net/npm/chart.js@4.4.1/dist/chart.umd.min.js"></script>
<style>
:root{--bg:#ffffff;--card:#FAF7F7;--line:#EBE7E8;--txt:#2D1B20;--sub:#827578;--accent:#C4506A;--accent2:#C4506A;}*{box-sizing:border-box}
body{margin:0;background:var(--bg);color:var(--txt);font-family:"Inter","PingFang TC","Apple LiGothic","STHeiti","Hiragino Sans GB",-apple-system,BlinkMacSystemFont,"Microsoft YaHei",sans-serif;line-height:1.5}
.wrap{max-width:1080px;margin:0 auto;padding:28px 20px 60px}
h1{font-size:24px;margin:0 0 4px;font-family:"DM Sans","Inter",sans-serif}.sub{color:var(--sub);font-size:13px;margin-bottom:22px}
.cards{display:grid;grid-template-columns:repeat(auto-fit,minmax(180px,1fr));gap:14px;margin-bottom:26px}
.card{background:var(--card);border:1px solid var(--line);border-radius:12px;padding:16px 18px}
.card .k{color:var(--sub);font-size:12px}
.card .v{font-size:22px;font-weight:600;margin-top:6px}
.panel{background:var(--card);border:1px solid var(--line);border-radius:12px;padding:18px;margin-bottom:22px}
.panel h2{font-size:16px;margin:0 0 14px}
table{width:100%;border-collapse:collapse;font-size:13px}
th,td{padding:9px 10px;text-align:left;border-bottom:1px solid var(--line)}
th{color:var(--sub);font-weight:500;font-size:12px}
td.num,th.num{text-align:right;font-variant-numeric:tabular-nums;font-family:"JetBrains Mono","Menlo",monospace}.pkg{font-family:"JetBrains Mono","Menlo","Consolas",monospace;font-size:12px;color:#333a45}.buyer-name{font-weight:600}
details{margin-top:6px}
summary{cursor:pointer;color:var(--accent);font-size:12px}
.foot{color:var(--sub);font-size:12px;margin-top:30px;border-top:1px solid var(--line);padding-top:14px}
.badge{display:inline-block;background:#e6eefc;color:var(--sub);border-radius:6px;padding:2px 8px;font-size:11px;margin-left:8px}
.chartbox{position:relative;height:300px}
</style>
<script src="https://cdn.jsdelivr.net/npm/xlsx@0.18.5/dist/xlsx.full.min.js"></script>
</head>
<body>
<div class="wrap">
<h1>武汉自投 · 投手投放花费报告 <span class="badge" id="weekBadge"></span></h1>
<div class="sub" id="metaLine">加载中…</div>
<div class="cards" id="cards"></div>
<div class="panel"><h2>各投手本周期内投放花费</h2><div class="chartbox"><canvas id="spendChart"></canvas></div></div>
<div class="panel"><h2>各投手主要订单 Package(花费最高)</h2><div class="chartbox"><canvas id="pkgChart"></canvas></div></div>
<div class="panel"><h2>投手明细</h2><div id="tables"></div></div>
<div class="foot" id="foot"></div>
</div>
<script>
const fmt=n=>n.toLocaleString('en-US',{minimumFractionDigits:2,maximumFractionDigits:2});
// 直接使用 data.json,Excel 支持由后续更新处理
fetch('data.json?t='+Date.now()).then(r=>r.json()).then(d=>render(d)).catch(e=>{document.getElementById('metaLine').textContent='数据加载失败:'+e.message;});
function render(d){
document.getElementById('weekBadge').textContent=d.meta.week||'';
document.getElementById('metaLine').textContent='数据周期:'+d.meta.date_range+' · 数据来源:'+d.meta.source+' · 生成时间:'+new Date(d.meta.generated_at).toLocaleString('zh-CN');
const buyers=d.buyers.slice().sort((a,b)=>b.total-a.total);
const cards=[['投手数',buyers.length],['投放花费合计',fmt(d.grand_total)],['覆盖 Adpingid 数',d.week34_id_count],['花费最高投手',buyers[0].name]];
document.getElementById('cards').innerHTML=cards.map(c=>'<div class="card"><div class="k">'+c[0]+'</div><div class="v">'+c[1]+'</div></div>').join('');
const palette=['#5b8cff','#ff9f5b','#4dd6a8','#c78bff','#ff6b81','#f5c451'];
new Chart(document.getElementById('spendChart'),{type:'bar',data:{labels:buyers.map(b=>b.name),datasets:[{label:'投放花费',data:buyers.map(b=>b.total),backgroundColor:buyers.map((b,i)=>palette[i%palette.length])}]},options:{indexAxis:'y',plugins:{legend:{display:false}},scales:{x:{ticks:{color:'#5b6472'},grid:{color:'#d6e2f5'}},y:{ticks:{color:'#111111'},grid:{display:false}}}}});
new Chart(document.getElementById('pkgChart'),{type:'bar',data:{labels:buyers.map(b=>b.name),datasets:[{label:'主要Package花费',data:buyers.map(b=>b.pkgs[0].spend),backgroundColor:'#4dd6a8'}]},options:{plugins:{legend:{display:false},tooltip:{callbacks:{afterLabel:(ctx)=>buyers[ctx.dataIndex].pkgs[0].pkg}}},scales:{x:{ticks:{color:'#111111'},grid:{display:false}},y:{ticks:{color:'#5b6472'},grid:{color:'#d6e2f5'}}}}});
document.getElementById('tables').innerHTML=buyers.map(b=>{
const rows=b.pkgs.map(p=>'<tr><td class="pkg">'+p.pkg+'</td><td class="num">'+fmt(p.spend)+'</td></tr>').join('');
return '<div style="margin-bottom:18px"><div class="buyer-name">'+b.name+' <span style="color:var(--sub);font-weight:400">合计 '+fmt(b.total)+' · 主要订单 '+b.pkgs[0].pkg+'</span></div><details><summary>展开 '+b.pkgs.length+' 个 Package 明细</summary><table><thead><tr><th>Package</th><th class="num">花费</th></tr></thead><tbody>'+rows+'</tbody></table></details></div>';
}).join('');
document.getElementById('foot').textContent=d.meta.note;
}
</script>
</body>
</html>