Commit Graph

6 Commits

Author SHA1 Message Date
xRangerDE
261aaa362e release: 5.0.4 — VOD-Hover: CSS geometry raus, JS allein authoritativ
Probleme der 5.0.3:
- CSS .vod-storyboard-preview hatte noch aspect-ratio:16/9, top:0, left:0, right:0
- JS hat dann inset:0 + aspect-ratio:auto inline gesetzt
- Im Electron-28-Chromium kam ein Layout-Konflikt raus -> Overlay-Box-
  Dimensions wichen von Host ab -> backgroundSize-Skalierung passte nicht
  zu visible-area -> mehrere Cells gleichzeitig sichtbar (Sprite-Sheet-
  Look statt Single-Cell-Preview)

Fix 5.0.4:
- CSS-Klasse hat NUR noch Visual+Stacking (opacity, transition, border-
  radius, overflow:hidden, z-index, position:absolute, pointer-events)
- KEIN top/left/right/bottom/width/height/aspect-ratio im CSS
- JS setzt alles inline und voll explicit: top=0, left=0, width=Xpx,
  height=Ypx aus hostRect (.vod-thumb-wrap)
- Sanity-Guards fuer width/height<=0 und cellWidth/cellHeight<=0
- scaleX und scaleY weiter unabhaengig fuer korrekte Cell-Box-Fuellung

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-13 14:53:00 +02:00
xRangerDE
a5a1d8c067 release: 5.0.3 — VOD hover overlay fuellt jetzt das gesamte Thumbnail-Wrap
Wechsel von explicit width/height auf inset:0 (top/right/bottom/left:0,
width/height:auto, aspect-ratio:auto override des CSS-Legacy 16/9). Damit
fuellt das Overlay garantiert das gesamte .vod-thumb-wrap — kein leerer
Streifen mehr am oberen oder unteren Rand der Hover-Vorschau, egal ob
Twitch Storyboard-Cell-Aspect oder Subpixel-Rendering minimal abweicht.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-13 14:44:39 +02:00
xRangerDE
11e2f957e6 release: 5.0.2 — VOD hover follow-ups
Fix 1: scaleX und scaleY werden jetzt unabhaengig berechnet. Twitch
Storyboard-Cells haben nicht zwingend 16:9; eine einheitliche scale-Variable
fuehrte zu Subpixel-Leakage am oberen oder unteren Rand mit Inhalt aus der
Nachbarzelle. Mit getrennter Achsen-Skalierung fuellt eine Cell die Overlay-
Box exakt.

Fix 2: Bulk-Select-Checkbox und Downloaded-Badge werden waehrend des Hover-
Previews ausgeblendet (vorher nur die Duration-Badge). Mein vorheriger Move
des Overlays in .vod-thumb-wrap hatte die Z-Order so geaendert, dass diese
Elemente jetzt sichtbar drueber lagen.

219 unit tests + e2e gruen.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-13 14:40:34 +02:00
xRangerDE
44daa65fe6 release: 5.0.1 — fix VOD hover preview + merge-group progress bar
Bug 1 — VOD-Hover Storyboard zeigte am unteren Rand einen statischen Streifen vom Original-Thumbnail (Subpixel-Mismatch + Aspect-Ratio-Konflikt). Fix: Overlay haengt jetzt an .vod-thumb-wrap statt .vod-card, mit explizitem width+height aus dem Thumbnail-BoundingRect — keine CSS-aspect-ratio-Interferenz mehr.

Bug 2 — Merge-Group Download zeigte einen eingefrorenen Progress-Bar bei Multi-Part-VODs (Part X/Y). Root Cause: der weighted-progress Wrapper clamped progress=-1 (HLS unknown-total 1s-Tick) auf 0, was overallProgress auf priorWeight fix-nagelte. Bar oszillierte zwischen indeterminate-animation und einem fixen ~10% Wert. Fix: lastVodProgress persistiert zwischen Path-A-Ticks und Path-B-Streamlink-%-Lines, sodass der Bar smooth waehrend einer Part hochzaehlt.

210 unit tests + e2e:release gruen.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-13 14:30:21 +02:00
xRangerDE
976ca40963 perf: bound the renderer-side VOD storyboard cache (FIFO 100)
vodStoryboardClientCache was a plain Map<vodId, VodStoryboard | null>
with no eviction. Every VOD ever hovered cached its first sprite
data URL — about 50-200 KB each. Browsing a long-running streamer's
2000-VOD archive could leave the renderer holding 100-400 MB of
hover-only sprite data permanently, with no signal to the user
that it was happening.

Wrapped writes in a rememberStoryboard helper that caps the cache
at 100 entries with FIFO eviction (Map iterator is insertion-ordered
so .keys().next().value is always the oldest). Cache hit / miss
semantics unchanged for the live set — only the dropped-off-the-
back entries get re-fetched if the user scrolls back to a VOD they
hovered hundreds of cards ago, and that re-fetch is fast because
the main-process side has its own metadata cache that survives the
renderer-side eviction.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 04:08:42 +02:00
xRangerDE
3c73efbad7 feat: banner background + live preview card + VOD hover storyboard + sticky header
Four interlocking visual upgrades that push the profile area from
"works" to "looks like a real Twitch app". Single release because
all four share data plumbing and need to land coherently.

1) Banner background — getStreamerProfile now also pulls
   bannerImageURL via public GQL, fetches the bytes server-side as a
   data URL (same path as the avatar fix in 4.6.18-4.6.19), and the
   renderer puts it behind the header content with blur(18px) +
   saturate(1.2) + a 0.55 opacity overlay. Result: per-streamer
   colour identity at a glance, like twitch.tv's channel page.

2) Live preview card — when isLive, the public-GQL stream block also
   carries previewImageURL(640x360), viewersCount, title, game{name}.
   A second card slides in below the main profile row showing the
   current frame at 240×135, eye-icon viewer count, big bold title,
   game, and a red "Jetzt aufnehmen" CTA. Click anywhere on the card
   OR on the button triggers triggerLiveRecording — same path as
   the sidebar REC dot, so the recording reaches the queue with
   identical settings.

3) VOD hover storyboard — Twitch ships a seekPreviewsURL per VOD
   pointing at a JSON manifest of sprite-sheet images, each a grid
   of preview thumbnails spanning the recording. New IPC
   get-vod-storyboard fetches the manifest, picks the high-quality
   first sprite, fetches its bytes as a data URL, and returns the
   grid metadata. Renderer (new renderer-vod-hover.ts) hooks
   delegated mouseover on #vodGrid: 220ms debounce, then on
   activation overlays a div positioned over the thumbnail with
   background-image=sprite + a setInterval cycling
   background-position through 4 evenly-spaced cells at 600ms each.
   Per-VOD result cached client-side so repeated hovers don't
   re-fetch. Negative results (private VODs, expired) are also
   cached so we don't re-query a known-empty manifest.

4) Sticky header — position:sticky;top:0;z-index:20 plus a
   backdrop-filter:blur(6px) so the VOD grid scrolling underneath
   reads through the banner subtly. Header stays anchored to the top
   of .content as the user scrolls hundreds of VODs.

GQL refresher: the public schema rejects `broadcasterType` but
accepts `roles{isPartner isAffiliate}`, plus the same query now
includes bannerImageURL and stream{previewImageURL viewersCount
title game{name}}. One single roundtrip pulls everything we need
for the header AND the live card. The old separate-follower-count
roundtrip (fetchOnlyFollowerCount) is now redundant but kept around
for back-compat in case other call sites grow into it.

Also: profile layout switched from one big flex row to a relative
container with two children (.streamer-profile-row for the meta,
.streamer-profile-live-card for the live block). The .live-card
only renders when isLive — offline streamers get the same compact
header they had before.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-11 00:55:17 +02:00