fix audio player freezing and improve UX

Switch WaveSurfer from MediaElement to WebAudio backend to prevent
WKWebView deadlocks that were freezing the entire Tauri app during
audio playback.

Reuse a single WaveSurfer instance across track changes instead of
destroying and recreating on every URL change, which was exhausting
the browser's AudioContext pool.

Other improvements:
- spacebar play/pause with capture phase to prevent history item activation
- drag-to-seek on waveform with silent scrub to avoid WebAudio popping
- slider always mounted to prevent layout shift during track transitions
- play button fills icon, accent bg when playing, loop button accent bg when active
- fix AudioBars animation getting stuck by keying on mode
- remove focus ring on history items
- sync slider position on pause and during seek
- remove title text from player bar
- thicker cursor (3px)
This commit is contained in:
Jamie Pine
2026-03-16 12:29:10 -07:00
parent 1526f2de26
commit 7dd70a52e4
3 changed files with 195 additions and 414 deletions
+2 -2
View File
@@ -64,7 +64,7 @@ function AudioBars({ mode }: { mode: 'idle' | 'generating' | 'playing' }) {
<div className="flex items-center gap-[2px] h-5">
{[0, 1, 2, 3, 4].map((i) => (
<motion.div
key={i}
key={`${mode}-${i}`}
className={`w-[3px] rounded-full ${barColor}`}
animate={
mode === 'generating'
@@ -440,7 +440,7 @@ export function HistoryTable() {
role={isPlayable ? 'button' : undefined}
tabIndex={isPlayable ? 0 : undefined}
className={cn(
'flex items-stretch gap-4 h-26 p-3',
'flex items-stretch gap-4 h-26 p-3 outline-none',
isPlayable && 'hover:bg-muted/70 cursor-pointer rounded-md',
isVersionsExpanded && 'rounded-b-none',
)}