Skip to content

[#1051] Fix airdrop chart label overlap via banded Y-axis#1052

Merged
realproject7 merged 1 commit intomainfrom
task/1051-banded-y-axis
May 5, 2026
Merged

[#1051] Fix airdrop chart label overlap via banded Y-axis#1052
realproject7 merged 1 commit intomainfrom
task/1051-banded-y-axis

Conversation

@realproject7
Copy link
Copy Markdown
Owner

Fixes #1051

Summary

The /airdrop chart from #1049 has the right concept (time-series, X=time, Y=MCap) but the pure log Y-axis math jams adjacent milestones together whenever their ratio is small relative to the total log range. In production the live page shows $50K — unlocks 100% overlapping $35K — unlocks 50%, and $10K — unlocks 30% overlapping $7K — unlocks 10%.

Replaces the log function mcapToY(mcap, yMin, yMax) with a piecewise-linear-banded Y-axis where each of the 4 milestones gets an equal 25% band of chart height. Within a band, position is log-interpolated between that band's lower and upper milestone values.

y from chart top:
   0%    diamond  ┐
        zone 3    │ gold→diamond, log-interp
  25%    gold    ─┤
        zone 2    │ silver→gold, log-interp
  50%    silver  ─┤
        zone 1    │ bronze→silver, log-interp
  75%    bronze  ─┤
        zone 0    │ floor→bronze, log-interp  (floor = bronze / 100)
 100%    floor    ┘

Milestone labels are anchored to band boundaries, so they're always 25% of chart height apart and cannot collide regardless of MCap ratios. Same chart geometry works for test mode and prod mode — only the milestone numeric values change.

Math sanity check (prod milestones $1M/$10M/$50M/$100M)

MCap Computed Y Visual position
$31K (current) 0.94 pre-bronze band, near chart bottom
$1M 0.75 bronze line
$10M 0.50 silver line
$50M 0.25 gold line
$100M 0.00 diamond line (chart top)

Other changes

  • Drop the Y-axis tick label column entirely. The right-edge milestone labels already convey what each band's top value is; stacking another column at the left edge re-introduces the overlap problem (and was where the spurious $50 floor label was coming from).
  • Add subtle alternating band stripes (4% accent fill on alternate bands) for zone separation.
  • Wrap right-edge milestone labels in <g className="hidden sm:block"> instead of putting Tailwind responsive classes directly on <text> elements (the latter is non-portable for SVG).
  • Diamond label rendered below its line (line is at chart top → above-line position would clip).

Files

  • src/components/airdrop/CampaignHero.tsx — replace mcapToY with makeMcapToY, drop Y-tick rendering, add band stripes, fix label wrapper.
  • package.json — version bump 1.6.1 → 1.6.2 (3rd digit, bug fix).

Test plan

  • npm run typecheck passes (verified)
  • npm run lint passes — no new errors/warnings on CampaignHero.tsx (verified)
  • At currentFdv=$31K prod milestones, heartbeat dot is in pre-bronze band (Y between 75% and 100% of chart height)
  • At currentFdv=$31K test milestones ($7K/$10K/$35K/$50K), dot is in silver→gold band (Y between 25% and 50%)
  • No two milestone labels overlap visually at any viewport ≥320px wide
  • No $50-style floor label artifact on the left edge
  • Mobile (<640px): right-edge labels hidden, mobile legend below chart shows all 4 milestones
  • Empty pl_daily_prices: chart frame + projection line + milestone lines + current dot still render

Reviewer note

Block this PR if it:

  • (a) reintroduces a single global Math.log10-based Y mapping over the whole [floor, diamond] range
  • (b) keeps Y-axis tick labels alongside right-edge milestone labels
  • (c) hardcodes any color hex

Replaces pure log Y-axis with piecewise-linear-banded Y where each of the
4 milestones (bronze/silver/gold/diamond) gets a fixed 25% band of chart
height. Within a band, position is log-interpolated between that band's
lower and upper milestone values.

Removes the Y-axis tick label column (the right-edge milestone labels are
already sufficient and stacking another column reintroduces overlap).
Adds subtle alternating band stripes for visual zone separation. Wraps
right-edge labels in a <g class="hidden sm:block"> to keep
responsive-class behavior consistent on SVG children.

Verified manually: at currentFdv=$31K with prod milestones
($1M/$10M/$50M/$100M) the heartbeat dot lands at Y≈94% (pre-bronze
band, near chart bottom); at $1M/$10M/$50M/$100M exactly it lands at
75/50/25/0% (band boundaries).

Fixes #1051

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@vercel
Copy link
Copy Markdown

vercel Bot commented May 5, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

1 Skipped Deployment
Project Deployment Actions Updated (UTC)
plotlink Ignored Ignored May 5, 2026 0:35am

Request Review

@realproject7 realproject7 merged commit 256a5b7 into main May 5, 2026
4 checks passed
@realproject7 realproject7 deleted the task/1051-banded-y-axis branch May 5, 2026 00:38
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Airdrop chart: fix overlapping milestone labels via banded Y-axis

1 participant