638 lines
29 KiB
HTML
638 lines
29 KiB
HTML
<!DOCTYPE html>
|
||
<html lang="en">
|
||
<head>
|
||
<link rel="icon" href="images/icon.ico" type="image/x-icon">
|
||
<meta charset="UTF-8">
|
||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||
<meta property="og:title" content="Daniel">
|
||
<meta property="og:description" content="A real-time rice difficulty calculator for 4k osu!mania. Displays dan level and tier from Alpha through to Theta with live strain graphs and MSD skillset breakdowns.">
|
||
<meta property="og:image" content="https://thebagelofman.github.io/Daniel/images/hero-screenshot.png">
|
||
<meta property="og:url" content="https://thebagelofman.github.io/Daniel">
|
||
<meta property="og:type" content="website">
|
||
<meta name="twitter:card" content="summary_large_image">
|
||
<meta name="description" content="A real-time rice difficulty calculator for 4k osu!mania. Displays dan level and tier from Alpha through to Theta with live strain graphs and MSD skillset breakdowns.">
|
||
<title>Daniel</title>
|
||
<style>
|
||
@import url('https://fonts.googleapis.com/css2?family=JetBrains+Mono:wght@300;400;500;700&display=swap');
|
||
|
||
:root {
|
||
--bg: #0e0f14;
|
||
--surface: #16181f;
|
||
--border: #2a2d3a;
|
||
--text: #dde1f5;
|
||
--muted: #626880;
|
||
--exact: #7dd3fc;
|
||
--adjacent: #4ade80;
|
||
--within: #fb923c;
|
||
--miss: #ef4444;
|
||
--accent: #818cf8;
|
||
}
|
||
|
||
*, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }
|
||
html { scroll-behavior: smooth; }
|
||
|
||
body {
|
||
background: var(--bg);
|
||
color: var(--text);
|
||
font-family: 'JetBrains Mono', monospace;
|
||
font-size: 14px;
|
||
line-height: 1.8;
|
||
}
|
||
|
||
a { color: var(--exact); text-decoration: none; }
|
||
a:hover { text-decoration: underline; }
|
||
|
||
.page {
|
||
max-width: 1100px;
|
||
margin: 0 auto;
|
||
padding: 0 32px;
|
||
}
|
||
|
||
/* ── Nav ─────────────────────────────────────────────────────────── */
|
||
nav {
|
||
border-bottom: 1px solid var(--border);
|
||
padding: 20px 0;
|
||
margin-bottom: 80px;
|
||
display: flex;
|
||
justify-content: space-between;
|
||
align-items: center;
|
||
}
|
||
.nav-logo { font-size: 16px; font-weight: 700; color: var(--text); }
|
||
.nav-logo span { color: var(--accent); }
|
||
.nav-links { display: flex; gap: 24px; list-style: none; }
|
||
.nav-links a {
|
||
font-size: 12px; color: var(--muted);
|
||
letter-spacing: 0.08em; text-transform: uppercase;
|
||
}
|
||
.nav-links a:hover { color: var(--text); text-decoration: none; }
|
||
|
||
/* ── Sections ────────────────────────────────────────────────────── */
|
||
section { margin-bottom: 80px; }
|
||
|
||
.section-tag {
|
||
font-size: 11px; color: var(--muted);
|
||
letter-spacing: 0.15em; text-transform: uppercase; margin-bottom: 8px;
|
||
}
|
||
|
||
h1 {
|
||
font-size: 52px; font-weight: 700; color: var(--text);
|
||
line-height: 1.05; letter-spacing: -0.02em; margin-bottom: 16px;
|
||
}
|
||
h1 span { color: var(--accent); }
|
||
|
||
h2 {
|
||
font-size: 20px; font-weight: 700; color: var(--text);
|
||
margin-bottom: 20px; padding-bottom: 10px; border-bottom: 1px solid var(--border);
|
||
}
|
||
|
||
h3 { font-size: 14px; font-weight: 500; color: var(--text); margin-bottom: 4px; }
|
||
|
||
p { color: var(--muted); margin-bottom: 16px; max-width: 600px; }
|
||
|
||
/* ── Buttons ─────────────────────────────────────────────────────── */
|
||
.btn {
|
||
display: inline-flex; align-items: center; gap: 8px;
|
||
padding: 10px 20px; font-family: 'JetBrains Mono', monospace;
|
||
font-size: 13px; cursor: pointer; border: 1px solid var(--border);
|
||
background: var(--surface); color: var(--text); text-decoration: none;
|
||
transition: border-color 0.15s, color 0.15s;
|
||
}
|
||
.btn:hover { border-color: var(--exact); color: var(--exact); text-decoration: none; }
|
||
.btn-primary { background: var(--exact); color: #0a0b0f; border-color: var(--exact); font-weight: 700; }
|
||
.btn-primary:hover { background: #a5e3fd; border-color: #a5e3fd; color: #0a0b0f; }
|
||
|
||
/* ── Hero ────────────────────────────────────────────────────────── */
|
||
.hero-desc { font-size: 15px; color: var(--muted); margin-bottom: 32px; max-width: 540px; }
|
||
.hero-actions { display: flex; gap: 12px; flex-wrap: wrap; margin-bottom: 80px; }
|
||
|
||
#hero {
|
||
position: relative;
|
||
overflow: hidden;
|
||
}
|
||
.hero-bg {
|
||
position: absolute;
|
||
right: 0;
|
||
top: 0;
|
||
bottom: auto;
|
||
height: 420px;
|
||
width: 800px;
|
||
background-image: url('./images/hero-screenshot.png');
|
||
background-size: cover;
|
||
background-position: right top;
|
||
opacity: 0.75;
|
||
pointer-events: none;
|
||
z-index: 0;
|
||
-webkit-mask-image: linear-gradient(to right, transparent 30%, black 70%);
|
||
mask-image: linear-gradient(to right, transparent 30%, black 70%);
|
||
}
|
||
#hero > *:not(.hero-bg) {
|
||
position: relative;
|
||
z-index: 1;
|
||
}
|
||
|
||
/* ── tab hint ────────────────────────────────────────────────────── */
|
||
.tab-hint {
|
||
font-size: 11px;
|
||
color: var(--muted);
|
||
letter-spacing: 0.08em;
|
||
margin-bottom: 12px;
|
||
}
|
||
.tab-hint code { font-size: 11px; }
|
||
|
||
/* ── Stat row ────────────────────────────────────────────────────── */
|
||
.stats-row {
|
||
display: flex; border: 1px solid var(--border); background: var(--surface);
|
||
}
|
||
.stat { flex: 1; padding: 20px 24px; border-right: 1px solid var(--border); }
|
||
.stat:last-child { border-right: none; }
|
||
.stat-val { font-size: 26px; font-weight: 700; display: block; line-height: 1; margin-bottom: 6px; }
|
||
.stat-lbl { font-size: 11px; color: var(--muted); letter-spacing: 0.08em; text-transform: uppercase; }
|
||
.c-exact { color: var(--exact); }
|
||
.c-adjacent { color: var(--adjacent); }
|
||
.c-within { color: var(--within); }
|
||
.c-muted { color: var(--muted); }
|
||
|
||
/* ── Steps list ──────────────────────────────────────────────────── */
|
||
.steps { border: 1px solid var(--border); }
|
||
.step { display: grid; grid-template-columns: 48px 1fr; border-bottom: 1px solid var(--border); }
|
||
.step:last-child { border-bottom: none; }
|
||
.step-num { font-size: 12px; color: var(--muted); padding: 20px 0 20px 16px; border-right: 1px solid var(--border); }
|
||
.step-body { padding: 20px 24px; }
|
||
.step-body p { font-size: 13px; margin-bottom: 0; max-width: 100%; }
|
||
|
||
code {
|
||
color: var(--exact); background: var(--bg);
|
||
border: 1px solid var(--border); padding: 1px 6px;
|
||
font-family: 'JetBrains Mono', monospace;
|
||
}
|
||
|
||
/* ── Feature list ────────────────────────────────────────────────── */
|
||
.features {
|
||
border: 1px solid var(--border);
|
||
margin-bottom: 32px;
|
||
}
|
||
.feature {
|
||
padding: 18px 20px;
|
||
border-bottom: 1px solid var(--border);
|
||
}
|
||
.feature:last-child { border-bottom: none; }
|
||
.feature h3 { font-size: 14px; margin-bottom: 2px; }
|
||
.feature p { font-size: 13px; margin-bottom: 0; max-width: 100%; }
|
||
|
||
/* ── Download block ──────────────────────────────────────────────── */
|
||
.download-block {
|
||
background: var(--surface); border: 1px solid var(--border);
|
||
padding: 28px; margin-bottom: 24px;
|
||
}
|
||
.dl-version {
|
||
font-size: 11px; color: var(--accent); letter-spacing: 0.1em;
|
||
background: rgba(129,140,248,0.1); border: 1px solid rgba(129,140,248,0.25);
|
||
padding: 2px 8px; display: inline-block; margin-bottom: 10px;
|
||
}
|
||
.dl-info p { font-size: 13px; margin-bottom: 0; }
|
||
.req-tags { display: flex; gap: 8px; flex-wrap: wrap; margin-top: 14px; }
|
||
.req-tag {
|
||
font-size: 12px; color: var(--muted);
|
||
background: var(--bg); border: 1px solid var(--border); padding: 2px 10px;
|
||
}
|
||
.dl-btn-row {
|
||
margin-top: 20px;
|
||
padding-top: 20px;
|
||
border-top: 1px solid var(--border);
|
||
display: flex;
|
||
align-items: center;
|
||
gap: 16px;
|
||
}
|
||
.dl-count {
|
||
font-size: 12px;
|
||
color: var(--muted);
|
||
}
|
||
.dl-count span {
|
||
color: var(--text);
|
||
}
|
||
|
||
/* ── Changelog ───────────────────────────────────────────────────── */
|
||
.changelog-entry {
|
||
display: grid; grid-template-columns: 140px 1fr;
|
||
gap: 24px; padding: 24px 0; border-bottom: 1px solid var(--border);
|
||
}
|
||
.changelog-entry:last-child { border-bottom: none; }
|
||
.cl-ver { font-size: 13px; color: var(--accent); }
|
||
.cl-date { font-size: 11px; color: var(--muted); margin-top: 4px; }
|
||
.cl-body ul { list-style: none; display: flex; flex-direction: column; gap: 4px; margin-top: 8px; }
|
||
.cl-body ul li { font-size: 13px; color: var(--muted); padding-left: 16px; position: relative; }
|
||
.cl-body ul li::before { content: '–'; position: absolute; left: 0; color: var(--border); }
|
||
|
||
.tag {
|
||
display: inline-block; font-size: 10px; letter-spacing: 0.08em;
|
||
padding: 1px 7px; margin-left: 8px; vertical-align: middle; text-transform: uppercase;
|
||
}
|
||
.tag.new { background: rgba(74,222,128,0.1); color: var(--adjacent); border: 1px solid rgba(74,222,128,0.2); }
|
||
.tag.fix { background: rgba(125,211,252,0.1); color: var(--exact); border: 1px solid rgba(125,211,252,0.2); }
|
||
.tag.breaking { background: rgba(239,68,68,0.1); color: var(--miss); border: 1px solid rgba(239,68,68,0.2); }
|
||
|
||
/* ── FAQ ─────────────────────────────────────────────────────────── */
|
||
.faq-item { border-bottom: 1px solid var(--border); }
|
||
.faq-item:first-child { border-top: 1px solid var(--border); }
|
||
.faq-q {
|
||
width: 100%; background: none; border: none; padding: 16px 0;
|
||
display: flex; justify-content: space-between; align-items: center;
|
||
cursor: pointer; font-family: 'JetBrains Mono', monospace;
|
||
font-size: 13px; color: var(--text); text-align: left; gap: 16px;
|
||
}
|
||
.faq-q:hover { color: var(--exact); }
|
||
.faq-arrow { font-size: 11px; color: var(--muted); flex-shrink: 0; transition: transform 0.2s; }
|
||
.faq-item.open .faq-arrow { transform: rotate(90deg); }
|
||
.faq-a { max-height: 0; overflow: hidden; transition: max-height 0.3s ease; }
|
||
.faq-item.open .faq-a { max-height: 300px; }
|
||
.faq-a p { font-size: 13px; padding-bottom: 16px; max-width: 100%; }
|
||
|
||
/* ── Stats CTA ───────────────────────────────────────────────────── */
|
||
.stats-cta {
|
||
background: var(--surface); border: 1px solid var(--border); padding: 28px;
|
||
display: flex; justify-content: space-between; align-items: center;
|
||
gap: 24px; flex-wrap: wrap; margin-bottom: 80px;
|
||
}
|
||
.stats-cta h3 { font-size: 15px; margin-bottom: 4px; }
|
||
.stats-cta p { font-size: 13px; margin-bottom: 0; }
|
||
|
||
/* ── Credits ─────────────────────────────────────────────────────── */
|
||
.credit-row {
|
||
display: grid; grid-template-columns: 160px 1fr;
|
||
gap: 24px; padding: 18px 0; border-bottom: 1px solid var(--border);
|
||
}
|
||
.credit-row:first-child { border-top: 1px solid var(--border); }
|
||
.credit-role { font-size: 11px; color: var(--muted); letter-spacing: 0.1em; text-transform: uppercase; padding-top: 2px; }
|
||
.credit-info h3 { font-size: 14px; margin-bottom: 2px; }
|
||
.credit-info p { font-size: 13px; margin-bottom: 0; }
|
||
|
||
/* ── Overlay screenshots ─────────────────────────────────────────── */
|
||
.overlay-screenshot {
|
||
width: 75%;
|
||
display: block;
|
||
margin: 12px auto 0;
|
||
}
|
||
|
||
/* ── Footer ──────────────────────────────────────────────────────── */
|
||
footer {
|
||
border-top: 1px solid var(--border); padding: 24px 0 48px;
|
||
display: flex; justify-content: space-between;
|
||
}
|
||
footer p { font-size: 12px; color: var(--muted); margin: 0; max-width: 100%; }
|
||
|
||
/* ── Responsive ──────────────────────────────────────────────────── */
|
||
@media (max-width: 600px) {
|
||
h1 { font-size: 36px; }
|
||
.stats-row { flex-direction: column; }
|
||
.stat { border-right: none; border-bottom: 1px solid var(--border); }
|
||
.changelog-entry, .credit-row { grid-template-columns: 1fr; gap: 8px; }
|
||
.stats-cta, .download-block { flex-direction: column; }
|
||
.nav-links { display: none; }
|
||
.dl-btn-row { flex-direction: column; align-items: flex-start; }
|
||
}
|
||
</style>
|
||
</head>
|
||
<body>
|
||
<div class="page">
|
||
|
||
<!-- Nav -->
|
||
<nav>
|
||
<div style="display:flex; align-items:center; gap:14px;">
|
||
<div class="nav-logo">Daniel</div>
|
||
<a href="https://www.youtube.com/@TheBagelOfMan/featured" target="_blank" title="YouTube" style="display:flex; align-items:center; color:var(--muted); transition:color 0.15s;" onmouseover="this.style.color='var(--text)'" onmouseout="this.style.color='var(--muted)'">
|
||
<svg xmlns="http://www.w3.org/2000/svg" width="18" height="18" viewBox="0 0 24 24" fill="currentColor">
|
||
<path d="M23.498 6.186a3.016 3.016 0 0 0-2.122-2.136C19.505 3.545 12 3.545 12 3.545s-7.505 0-9.377.505A3.017 3.017 0 0 0 .502 6.186C0 8.07 0 12 0 12s0 3.93.502 5.814a3.016 3.016 0 0 0 2.122 2.136c1.871.505 9.376.505 9.376.505s7.505 0 9.377-.505a3.015 3.015 0 0 0 2.122-2.136C24 15.93 24 12 24 12s0-3.93-.502-5.814zM9.545 15.568V8.432L15.818 12l-6.273 3.568z"/>
|
||
</svg>
|
||
</a>
|
||
<a href="https://github.com/TheBagelOfMan/Daniel" target="_blank" title="GitHub" style="display:flex; align-items:center; color:var(--muted); transition:color 0.15s;" onmouseover="this.style.color='var(--text)'" onmouseout="this.style.color='var(--muted)'">
|
||
<svg xmlns="http://www.w3.org/2000/svg" width="18" height="18" viewBox="0 0 24 24" fill="currentColor">
|
||
<path d="M12 0C5.374 0 0 5.373 0 12c0 5.302 3.438 9.8 8.207 11.387.599.111.793-.261.793-.577v-2.234c-3.338.726-4.033-1.416-4.033-1.416-.546-1.387-1.333-1.756-1.333-1.756-1.089-.745.083-.729.083-.729 1.205.084 1.839 1.237 1.839 1.237 1.07 1.834 2.807 1.304 3.492.997.107-.775.418-1.305.762-1.604-2.665-.305-5.467-1.334-5.467-5.931 0-1.311.469-2.381 1.236-3.221-.124-.303-.535-1.524.117-3.176 0 0 1.008-.322 3.301 1.23A11.509 11.509 0 0 1 12 5.803c1.02.005 2.047.138 3.006.404 2.291-1.552 3.297-1.23 3.297-1.23.653 1.653.242 2.874.118 3.176.77.84 1.235 1.911 1.235 3.221 0 4.609-2.807 5.624-5.479 5.921.43.372.823 1.102.823 2.222v3.293c0 .319.192.694.801.576C20.566 21.797 24 17.3 24 12c0-6.627-5.373-12-12-12z"/>
|
||
</svg>
|
||
</a>
|
||
</div>
|
||
<ul class="nav-links">
|
||
<li><a href="#how-it-works">How it works</a></li>
|
||
<li><a href="#download">Download</a></li>
|
||
<li><a href="#changelog">Changelog</a></li>
|
||
<li><a href="#faq">FAQ</a></li>
|
||
<li><a href="#credits">Credits</a></li>
|
||
</ul>
|
||
</nav>
|
||
|
||
<!-- Hero -->
|
||
<section id="hero">
|
||
<div class="hero-bg"></div>
|
||
<h1>Daniel</h1>
|
||
<p style="font-size:11px; color:var(--muted); letter-spacing:0.12em; text-transform:uppercase; margin-bottom:12px;">
|
||
Difficulty Analysis of Notechart Intensity for Estimated Levels
|
||
</p>
|
||
<p class="hero-desc">
|
||
A real-time rice difficulty calculator for 4k osu!mania. Daniel links up to <a href="https://github.com/tosuapp/tosu" target="_blank">tosu</a> to read
|
||
your currently selected beatmap displaying its dan referenced level and its tier (Low/Mid/High) from Alpha through to Theta. It breaks it down further using a live strain graph and individual MSD skillsets.
|
||
</p>
|
||
<div class="hero-actions">
|
||
<a href="#download" class="btn btn-primary">↓ Download for Windows</a>
|
||
<a href="benchmark_report.html" class="btn">◈ Benchmark stats</a>
|
||
</div>
|
||
<div class="stats-row">
|
||
<div class="stat">
|
||
<span class="stat-val c-exact" id="stat-exact">52.4%</span>
|
||
<div class="stat-lbl">Within Exact Tier</div>
|
||
</div>
|
||
<div class="stat">
|
||
<span class="stat-val c-adjacent" id="stat-adjacent">89.6%</span>
|
||
<div class="stat-lbl">Within Adjacent Tiers</div>
|
||
</div>
|
||
<div class="stat">
|
||
<span class="stat-val c-within" id="stat-within">98.7%</span>
|
||
<div class="stat-lbl">Within one full dan Level</div>
|
||
</div>
|
||
<div class="stat">
|
||
<span class="stat-val c-muted" id="stat-maps">145</span>
|
||
<div class="stat-lbl">Beatmaps tested</div>
|
||
</div>
|
||
</div>
|
||
</section>
|
||
|
||
<!-- How it works -->
|
||
<section id="how-it-works">
|
||
<h2>How it works!</h2>
|
||
<div class="feature">
|
||
<h3>Real-time Detection</h3>
|
||
<p>Daniel reads map data live in real-time using tosu. This means that whenever you change beatmap Daniel will update instantly!</p>
|
||
</div>
|
||
<div class="feature">
|
||
<h3>Modified Sunny Rework Algorithm</h3>
|
||
<p>The numerical dan rating is calculated using a modified version of the Sunny Rework algorithm which is optimised for high-level rice. Long notes and OD are not factored into the calculation. The numerical dan ratings are based of individual maps which leads to marathons usually displaying the 'High' tier within that dan level.</p>
|
||
</div>
|
||
<div class="feature">
|
||
<h3>Skillset Detection via MSD</h3>
|
||
<p>Individual skillsets are calculated using MSD (MinaCalc Skill Difficulty). Overall rating is also calculated and jackspeed is used to determine whether a beatmap is primarily vibro based.</p>
|
||
</div>
|
||
<div class="feature">
|
||
<h3>Mod Support</h3>
|
||
<p>HT and DT are both supported as the rating adjusts automatically based on the selected mod.</p>
|
||
</div>
|
||
|
||
<h3 style="margin: 32px 0 6px; font-size:13px; color:var(--muted); letter-spacing:0.1em; text-transform:uppercase;">Overlay views</h3>
|
||
<p class="tab-hint">You can press <code>Tab</code> to cycle between the overlay views.</p>
|
||
<div class="steps">
|
||
<div class="step" style="display:block; padding:0;">
|
||
<div class="step-body" style="padding:20px 24px 0">
|
||
<h3>Compact</h3>
|
||
<p style="margin-bottom:0">A minimalistic display showing only the estimated dan plus the numerical rating.</p>
|
||
</div>
|
||
<img src="./images/compact.png" alt="Compact view" class="overlay-screenshot">
|
||
</div>
|
||
<div class="step" style="display:block; padding:0; border-top:1px solid var(--border)">
|
||
<div class="step-body" style="padding:20px 24px 0">
|
||
<h3>Statistics</h3>
|
||
<p style="margin-bottom:0">The compact view with added MSD skillset calculations for skillsets and overall MSD rating.</p>
|
||
</div>
|
||
<img src="./images/statistics.png" alt="Statistics view" class="overlay-screenshot">
|
||
</div>
|
||
<div class="step" style="display:block; padding:0; border-top:1px solid var(--border)">
|
||
<div class="step-body" style="padding:20px 24px 0">
|
||
<h3>Graph</h3>
|
||
<p style="margin-bottom:0">The statistics view with an added straintime graph that
|
||
updates in real-time based on drain time in the beatmap. Red vertical lines indicate pauses in gameplay.</p>
|
||
</div>
|
||
<img src="./images/graph.png" alt="Graph view" class="overlay-screenshot">
|
||
</div>
|
||
</div>
|
||
</section>
|
||
|
||
<!-- Download -->
|
||
<section id="download">
|
||
<h2>Download</h2>
|
||
<div class="download-block">
|
||
<div class="dl-info">
|
||
<h3 id="dl-filename">Daniel.exe</h3>
|
||
<div class="dl-version" id="dl-version">Loading...</div>
|
||
<p>Requirements:</p>
|
||
<div class="req-tags">
|
||
<span class="req-tag">Windows 10 / 11</span>
|
||
<span class="req-tag">osu! / osu!(stable)</span>
|
||
<span class="req-tag">tosu</span>
|
||
</div>
|
||
</div>
|
||
<div class="dl-btn-row">
|
||
<a href="#" id="dl-btn" class="btn btn-primary">↓ Download .exe</a>
|
||
<span class="dl-count"><span id="download-count">...</span> downloads</span>
|
||
</div>
|
||
</div>
|
||
|
||
<div class="steps">
|
||
<div class="step">
|
||
<div class="step-num">01</div>
|
||
<div class="step-body">
|
||
<h3>Install tosu</h3>
|
||
<p> Download and install <a href="https://github.com/tosuapp/tosu" target="_blank">tosu</a>.</p>
|
||
</div>
|
||
</div>
|
||
<div class="step">
|
||
<div class="step-num">02</div>
|
||
<div class="step-body">
|
||
<h3>Download Daniel</h3>
|
||
<p>Save <code id="dl-filename-step">Daniel.exe</code> anywhere on your system.</p>
|
||
</div>
|
||
</div>
|
||
<div class="step">
|
||
<div class="step-num">03</div>
|
||
<div class="step-body">
|
||
<h3>Launch tosu and Daniel</h3>
|
||
<p>Run both tosu and Daniel alongside your osu! client.</p>
|
||
</div>
|
||
</div>
|
||
<div class="step">
|
||
<div class="step-num">04</div>
|
||
<div class="step-body">
|
||
<h3>Have fun danning with Daniel</h3>
|
||
<p>Boy do I love me some dans.</p>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
</section>
|
||
|
||
<!-- Changelog -->
|
||
<section id="changelog">
|
||
<h2>Changelog</h2>
|
||
<div id="changelog-entries">
|
||
<div style="color:var(--muted); font-size:13px;">Loading...</div>
|
||
</div>
|
||
</section>
|
||
|
||
<!-- FAQ -->
|
||
<section id="faq">
|
||
<h2>FAQ</h2>
|
||
|
||
<div class="faq-item">
|
||
<button class="faq-q">How well does it calculate vibro? <span class="faq-arrow">▶</span></button>
|
||
<div class="faq-a"><p>It will refuse to calculate vibro maps altogether and will just list them as 'VIBRO'. To my knowledge this doesn't affect any maps other than just straight vibro.</p></div>
|
||
</div>
|
||
|
||
<div class="faq-item">
|
||
<button class="faq-q">Does it affect in game performance? <span class="faq-arrow">▶</span></button>
|
||
<div class="faq-a"><p>All calculations are done when the beatmap is first selected so any performance hits would only be in the song select menu.</p></div>
|
||
</div>
|
||
|
||
<div class="faq-item">
|
||
<button class="faq-q">How does the straintime graph work? <span class="faq-arrow">▶</span></button>
|
||
<div class="faq-a"><p>The graph is based on the same modified Sunny Rework algorithm that's used for the numerical dan values. This means that it represents that actual difficulty of that point in the beatmap rather than the density.</p></div>
|
||
</div>
|
||
|
||
<div class="faq-item">
|
||
<button class="faq-q">Is the source code available? <span class="faq-arrow">▶</span></button>
|
||
<div class="faq-a"><p>Source code is available <a href="https://github.com/TheBagelOfMan/Daniel" target="_blank">here!</a></p></div>
|
||
</div>
|
||
|
||
<div class="faq-item">
|
||
<button class="faq-q">What patterns is it bad at calculating? <span class="faq-arrow">▶</span></button>
|
||
<div class="faq-a"><p>It's bad at quite a few different skillsets in particular. It heavily underrates speedjack (Vertex Beta Zeta) and awkward speed (Volcanic). It overrates in epsilon+ anchorjack and may also overrate some high bpm speed(Finixe Zeta). There are more patterns it struggles with occasionally but these are the most consistent ones.</p></div>
|
||
</div>
|
||
|
||
<div class="faq-item">
|
||
<button class="faq-q">Does it calculate long notes? <span class="faq-arrow">▶</span></button>
|
||
<div class="faq-a"><p>No. It used to in testing versions but all LNs are converted to rice for the calculations now.</p></div>
|
||
</div>
|
||
|
||
<div class="faq-item">
|
||
<button class="faq-q">Does it factor in OD into the calculation? <span class="faq-arrow">▶</span></button>
|
||
<div class="faq-a"><p>No. It used to in testing versions but now all maps are calculated as if they are OD9.</p></div>
|
||
</div>
|
||
|
||
<div class="faq-item">
|
||
<button class="faq-q">Will you make an LN dan calculator? <span class="faq-arrow">▶</span></button>
|
||
<div class="faq-a"><p>Maybe but not confirmed.</p></div>
|
||
</div>
|
||
</section>
|
||
|
||
<!-- Credits -->
|
||
<section id="credits">
|
||
<h2>Credits</h2>
|
||
<div class="credit-row">
|
||
<div class="credit-role">Developer</div>
|
||
<div class="credit-info">
|
||
<h3>TheBagelOfMan</h3>
|
||
</div>
|
||
</div>
|
||
<div class="credit-row">
|
||
<div class="credit-role"><a href="https://github.com/sunnyxxy/Star-Rating-Rebirth" target="_blank">Sunny Rework Algorithm Used</a></div>
|
||
<div class="credit-info">
|
||
<h3>[Crz]sunnyxxy, Natelytle, vernonlim, ChlorieHCl, Imperial Wolf</h3>
|
||
</div>
|
||
</div>
|
||
<div class="credit-row">
|
||
<div class="credit-role"><a href="https://github.com/etternagame/etterna" target="_blank">MSD algorithm</a></div>
|
||
<div class="credit-info">
|
||
<h3>MinaciousGrace</h3>
|
||
</div>
|
||
</div>
|
||
<div class="credit-row">
|
||
<div class="credit-role"><a href="https://github.com/tosuapp/tosu" target="_blank">tosu</a></div>
|
||
<div class="credit-info">
|
||
<h3>KotRik, Cherry</h3>
|
||
</div>
|
||
</div>
|
||
</section>
|
||
|
||
<!-- Footer -->
|
||
<footer>
|
||
<p>Daniel Daniel Daniel Daniel Daniel</p>
|
||
<p id="footer-version">...</p>
|
||
</footer>
|
||
|
||
</div>
|
||
|
||
<script>
|
||
document.querySelectorAll('.faq-q').forEach(btn => {
|
||
btn.addEventListener('click', () => {
|
||
const item = btn.closest('.faq-item');
|
||
const isOpen = item.classList.contains('open');
|
||
document.querySelectorAll('.faq-item.open').forEach(el => el.classList.remove('open'));
|
||
if (!isOpen) item.classList.add('open');
|
||
});
|
||
});
|
||
|
||
fetch('benchmark_report.html')
|
||
.then(r => r.text())
|
||
.then(html => {
|
||
const doc = new DOMParser().parseFromString(html, 'text/html');
|
||
const vals = doc.querySelectorAll('.stat-val');
|
||
if (vals.length >= 5) {
|
||
const exact = vals[0].textContent.trim();
|
||
const adjacent = vals[1].textContent.trim();
|
||
const within = vals[2].textContent.trim();
|
||
const maps = vals[4].textContent.trim();
|
||
const exactN = parseFloat(exact);
|
||
const adjacentN = parseFloat(adjacent);
|
||
const withinN = parseFloat(within);
|
||
document.getElementById('stat-exact').textContent = exact;
|
||
document.getElementById('stat-adjacent').textContent = (exactN + adjacentN).toFixed(1) + '%';
|
||
document.getElementById('stat-within').textContent = (exactN + adjacentN + withinN).toFixed(1) + '%';
|
||
document.getElementById('stat-maps').textContent = maps;
|
||
|
||
}
|
||
})
|
||
.catch(() => {});
|
||
|
||
fetch('https://api.github.com/repos/TheBagelOfMan/Daniel/releases')
|
||
.then(r => r.json())
|
||
.then(releases => {
|
||
let total = 0;
|
||
releases.forEach(r => r.assets.forEach(a => total += a.download_count));
|
||
document.getElementById('download-count').textContent = total.toLocaleString();
|
||
|
||
const latest = releases[0];
|
||
if (!latest) return;
|
||
|
||
const version = latest.tag_name;
|
||
const exeAsset = latest.assets.find(a => a.name.endsWith('.exe'));
|
||
const downloadUrl = exeAsset
|
||
? exeAsset.browser_download_url
|
||
: `https://github.com/TheBagelOfMan/Daniel/releases/latest`;
|
||
const filename = exeAsset ? exeAsset.name : 'Daniel.exe';
|
||
|
||
document.getElementById('dl-version').textContent = `${version} - Latest`;
|
||
document.getElementById('dl-filename').textContent = filename;
|
||
document.getElementById('dl-btn').href = downloadUrl;
|
||
document.getElementById('dl-filename-step').textContent = filename;
|
||
document.getElementById('footer-version').textContent = version;
|
||
|
||
const changelogEl = document.getElementById('changelog-entries');
|
||
if (releases.length === 0) {
|
||
changelogEl.innerHTML = '<div style="color:var(--muted); font-size:13px;">No releases found.</div>';
|
||
} else {
|
||
changelogEl.innerHTML = releases.map((r, i) => {
|
||
const date = new Date(r.published_at).toLocaleDateString('en-GB', { year: 'numeric', month: 'long', day: 'numeric' });
|
||
const bodyHtml = r.body
|
||
? r.body
|
||
.split('\n')
|
||
.filter(l => l.trim())
|
||
.map(l => {
|
||
const stripped = l.replace(/^[-*]\s*/, '').replace(/\*\*(.*?)\*\*/g, '$1').trim();
|
||
return `<li>${stripped}</li>`;
|
||
})
|
||
.join('')
|
||
: '<li>No release notes.</li>';
|
||
return `
|
||
<div class="changelog-entry">
|
||
<div>
|
||
<div class="cl-ver">${r.tag_name}${i === 0 ? ' <span class="tag new">latest</span>' : ''}</div>
|
||
<div class="cl-date">${date}</div>
|
||
</div>
|
||
<div class="cl-body"><ul>${bodyHtml}</ul></div>
|
||
</div>`;
|
||
}).join('');
|
||
}
|
||
})
|
||
.catch(() => {
|
||
document.getElementById('download-count').textContent = '–';
|
||
document.getElementById('dl-version').textContent = 'latest';
|
||
document.getElementById('dl-btn').href = 'https://github.com/TheBagelOfMan/Daniel/releases/latest';
|
||
document.getElementById('footer-version').textContent = '–';
|
||
});
|
||
</script>
|
||
<script data-goatcounter="https://thebagelofman.goatcounter.com/count" async src="//gc.zgo.at/count.js"></script>
|
||
</body>
|
||
</html> |