Inspiration
Language learning apps have a retention problem. You open Duolingo, tap through a few exercises about "the apple is red," close it, and forget everything by morning. The issue isn't motivation — it's that the content has no emotional hook. Meanwhile, you'll listen to the same Bad Bunny song forty times in a week and absorb nothing, because there's no structure forcing you to engage with the words. We kept thinking: what if those two things were the same app? The insight was that music already does the hard part — it makes repetition feel good. All Lyric2Lang had to do was attach the learning to the moment the line is playing, before you have a chance to tune it out.
What it does
Lyric2Lang plays a song in your target language and pauses it line by line, turning each lyric into a micro-exercise before the music continues. You pick your language pair — Spanish to English, French to English, English to French, any of the six combinations — choose a song from artists like Bad Bunny, Stromae, or Katy Perry, and the app takes it from there. While a line plays, you see it highlighted Apple Music-style with a live translation below: the active line large and bold, upcoming lines fading in a cascade, past lines ghosted out. When the line ends, the player pauses and an exercise slides up — tap to match words, reassemble the translation from a word bank, fill in the blank, or identify what you just heard from four options. Get it right and the music resumes from exactly where it stopped. Every eighth line triggers a Lightning Round: 30 seconds of rapid-fire vocabulary matching scored against a countdown timer. XP accumulates with a combo multiplier, hearts track your accuracy, and a global leaderboard ranks you against other learners by weekly score. The full song library covers six tracks across three languages — Nuevayol and Hips Don't Lie for Spanish, Alors on Danse and Tout Oublier for French, Roar and Firework for English — with a library of locked songs signalling what comes next.
How we built it
Lyric2Lang is a Next.js 16 App Router application written in TypeScript, with Tailwind CSS v4 for styling, Framer Motion v12 for animations, and Zustand v5 for global state. The core game engine lives in a single useGameEngine hook that manages a state machine cycling through four phases: playing, paused-for-exercise, feedback, and complete. A 200ms polling interval watches the YouTube iframe's getCurrentTime() — there's no native threshold event in the YouTube IFrame API, so polling is the only reliable approach — and triggers a pause when playback crosses the midpoint of the next lyric line's timestamp. Lyric timing comes from lrclib.net's free API, which returns LRC-format synchronized lyrics for most commercial songs, parsed into timestamped line objects and merged with pre-stored translations. Exercise content is generated on the fly by Claude Haiku: a structured prompt per exercise type returns strict JSON — word pairs, word banks, fill-in-blank options, listening distractors — validated before rendering, with a hardcoded fallback exercise set for every demo song as a silent safety net. To keep the API key server-side, all Claude calls go through a /api/exercise route rather than hitting Anthropic directly from the browser. Both the server and browser cache exercises by ${songId}-${lineIndex}-${type} so Claude is never called twice for the same line in the same session. The Apple Music lyric display effect uses canvas color sampling on the YouTube thumbnail to extract the album's dominant hue, applied as a radial gradient background that transitions across songs. When an exercise overlay opens, the lyric view blurs behind it using a CSS filter transition — the music world stays present but paused.
Challenges we ran into
The hardest problem was synchronization. YouTube's iframe API doesn't fire events when playback crosses a timestamp — you poll, which means every exercise trigger, lyric highlight, and feedback moment depends on a tight loop that stays accurate without thrashing the browser. Getting the 200ms interval right — and ensuring the single YouTubePlayer instance stays mounted so the polling loop never drops — took more care than expected. On mobile this meant positioning the iframe off-screen at fixed; top: -9999px while showing a visual thumbnail pill in its place, so audio and timing continue running invisibly in the background. The other challenge was exercise quality. Claude generates exercises on the fly, but a word-match for a four-word line with simple vocabulary produces trivially easy pairs. We invested in prompt engineering — every prompt explicitly states the song language (Spanish, French, or English, resolved from song.language in the song definitions) and requires distractors that are plausible rather than obviously wrong. We also hit a React 19 constraint: useGameEngine updates Zustand state (XP, hearts) in response to answers, but React 19 disallows side effects inside setState updaters. The fix was maintaining a stateRef mirror of game state so submitAnswer can call external Zustand updates outside the updater function entirely.
Accomplishments that we're proud of
The Apple Music lyric view is the thing we're most proud of technically. The progressive opacity fade, the active line anchored at 35% from the top of the scroll container, the background color shifting to match the album art — it took real iteration to feel as natural as it does. More than the visual, we're proud that the core loop is genuinely fun to play. The moment the song pauses and the exercise slides up has a satisfying quality — the music world is still there, blurred behind the card, and the only thing between you and hearing the next line is answering one question correctly. That tension is the product, and it works.
What we learned
We learned that the exercise-to-audio transition is everything. Early versions just stopped the player and showed a card, which felt punishing. The breakthrough was keeping the lyric view visible and blurred behind the overlay — it communicates "paused, not gone," which changes the feel entirely. We also learned that language learning and dopamine engineering aren't as separate as they sound. The combo multiplier, the XP pop animation, the Lightning Round energy — none of that is decoration. It's what makes someone answer a fifth question when they'd have closed a traditional flashcard app after the second. On the technical side, building around a polling loop taught us how much hidden state management complexity comes from bridging a third-party iframe with a React state machine — the stateRef pattern we landed on for React 19 compatibility is something we'll carry into future projects.
What's next for LyricLang
The architecture is already built to scale. Replacing localStorage with Supabase would take the leaderboard from seeded demo data to a real global ranking with persistent accounts across devices. The singing mode already has a "Coming Soon" slot in the UI — Web Speech API speech-to-text can match spoken words against lyric text for a full karaoke-with-grading feature without needing pitch detection libraries. A spaced repetition system layered on top of the session data would track which words a user misses across songs and resurface them in future exercises, turning passive exposure into lasting vocabulary retention. Word-level highlighting — individual words in the active lyric line lighting up one by one in sync with the audio, timed by dividing the line's duration by its word count — is the feature that would make Lyric2Lang feel fully native to music rather than attached to it. On the content side, the song library is designed to expand: the six demoable tracks are a foundation, not a ceiling. Korean with BTS, Portuguese with Anitta, Italian with Mahmood — each new language is a new artist relationship and a new learner demographic. Longer term, the Claude API integration opens an adaptive difficulty path: analyzing answer patterns over sessions to identify which grammar structures a user consistently misses and generating targeted exercise batches around those specific weak spots, rather than cycling through the same four exercise types in fixed rotation. The north star is a learner who finishes a song and realizes they've absorbed thirty words of a new language without ever feeling like they were studying.
Built With
- claude
- css
- framer
- next.js
- react
- reform
- tailwind
- typescript
Log in or sign up for Devpost to join the conversation.