From 4462b44e9b060f9da809cec1372a46e13ee6bc99 Mon Sep 17 00:00:00 2001 From: edde746 <86283021+edde746@users.noreply.github.com> Date: Fri, 26 Jun 2026 07:57:21 +0200 Subject: [PATCH] fix: show server name on TV hubs with multiple servers close #1319 --- lib/screens/discover_screen.dart | 3 ++ lib/widgets/tv_browse_rail.dart | 48 +++++++++++++++++++++++++------- 2 files changed, 41 insertions(+), 10 deletions(-) diff --git a/lib/screens/discover_screen.dart b/lib/screens/discover_screen.dart index ac1d23e3..6d3fbcf0 100644 --- a/lib/screens/discover_screen.dart +++ b/lib/screens/discover_screen.dart @@ -1210,6 +1210,8 @@ class _DiscoverScreenState extends State final theme = Theme.of(context); final svc = SettingsService.instance; final hideSpoilers = svc.read(SettingsService.hideSpoilers); + final showServerNameOnHubs = svc.read(SettingsService.showServerNameOnHubs); + final hubsSpanMultipleServers = _hubsSpanMultipleServers(); final browseHubs = _tvBrowseHubs; final scale = TvLayoutConstants.scaleForSize(size); // Only layout-aspect (flip-stable) scope values may be read here: an @@ -1308,6 +1310,7 @@ class _DiscoverScreenState extends State child: TvBrowseRail( key: _tvBrowseRailKey, hubs: browseHubs, + showServerName: showServerNameOnHubs || hubsSpanMultipleServers, iconForHub: (hub, _) => hub.id == 'continue_watching' ? Symbols.play_circle_rounded : _getHubIcon(hub.title), onFocusedItemChanged: _setSpotlightItem, diff --git a/lib/widgets/tv_browse_rail.dart b/lib/widgets/tv_browse_rail.dart index f7d4c77d..02b0662d 100644 --- a/lib/widgets/tv_browse_rail.dart +++ b/lib/widgets/tv_browse_rail.dart @@ -297,6 +297,11 @@ enum TvRailTrailing { none, loading, error, viewAll } class TvBrowseRail extends StatefulWidget { final List hubs; final IconData Function(MediaHub hub, int index) iconForHub; + + /// Whether to show each hub's originating server name in its header. Used when + /// the loaded hubs span more than one connected server so their origin stays + /// clear, mirroring the mobile [HubSection] behavior. + final bool showServerName; final ValueChanged? onFocusedItemChanged; final void Function(MediaHub hub, MediaItem item)? onFocusedHubItemChanged; final void Function(String)? onRefresh; @@ -340,6 +345,7 @@ class TvBrowseRail extends StatefulWidget { super.key, required this.hubs, required this.iconForHub, + this.showServerName = false, this.onFocusedItemChanged, this.onFocusedHubItemChanged, this.onRefresh, @@ -1174,6 +1180,14 @@ class TvBrowseRailState extends State { final colorScheme = Theme.of(context).colorScheme; final titleColor = isActive ? colorScheme.onSurface : colorScheme.onSurface.withValues(alpha: 0.54); final iconColor = isActive ? colorScheme.onSurface : colorScheme.onSurface.withValues(alpha: 0.42); + final showServerName = widget.showServerName && hub.serverName != null; + final serverColor = colorScheme.primary.withValues(alpha: isActive ? 0.7 : 0.4); + final serverStyle = Theme.of(context).textTheme.titleMedium?.copyWith( + color: serverColor, + fontSize: 15 * scale, + height: 1, + fontWeight: FontWeight.w700, + ); return SizedBox( height: TvBrowseRailLayout.hubStripHeightForScale(scale), @@ -1185,16 +1199,30 @@ class TvBrowseRailState extends State { AppIcon(widget.iconForHub(hub, hubIndex), fill: 1, size: 20 * scale, color: iconColor), SizedBox(width: 8 * scale), Expanded( - child: Text( - hub.title, - maxLines: 1, - overflow: .ellipsis, - style: Theme.of(context).textTheme.titleMedium?.copyWith( - color: titleColor, - fontSize: 18 * scale, - height: 1, - fontWeight: isActive ? FontWeight.w800 : FontWeight.w700, - ), + child: Row( + children: [ + Flexible( + child: Text( + hub.title, + maxLines: 1, + overflow: .ellipsis, + style: Theme.of(context).textTheme.titleMedium?.copyWith( + color: titleColor, + fontSize: 18 * scale, + height: 1, + fontWeight: isActive ? FontWeight.w800 : FontWeight.w700, + ), + ), + ), + if (showServerName) ...[ + SizedBox(width: 8 * scale), + Text('•', style: serverStyle), + SizedBox(width: 8 * scale), + Flexible( + child: Text(hub.serverName!, maxLines: 1, overflow: .ellipsis, style: serverStyle), + ), + ], + ], ), ), if (_trailingFor(hub) == TvRailTrailing.viewAll) ...[