This commit is contained in:
Dan Long
2025-12-31 00:23:47 -06:00
3 changed files with 29 additions and 17 deletions
+15 -5
View File
@@ -305,11 +305,21 @@ class PlayerNative implements Player {
}
void _updateSelectedSubtitleTrack(dynamic trackId) {
_updateSelectedTrack<SubtitleTrack>(
trackId,
_state.tracks.subtitle.cast<SubtitleTrack?>().toList(),
(selection, track) => selection.copyWith(subtitle: track),
);
final id = trackId?.toString();
SubtitleTrack? selectedTrack;
if (id == null || id == 'no') {
// Explicitly set SubtitleTrack.off so episode navigation can detect "subtitles off"
selectedTrack = SubtitleTrack.off;
} else {
selectedTrack = _state.tracks.subtitle.cast<SubtitleTrack?>().firstWhere(
(t) => t?.id == id,
orElse: () => null,
);
}
_state = _state.copyWith(track: _state.track.copyWith(subtitle: selectedTrack));
_trackController.add(_state.track);
}
void _updateSelectedTrack<T>(
+5 -1
View File
@@ -41,6 +41,8 @@ class _SeasonDetailScreenState extends State<SeasonDetailScreen> with ItemUpdata
List<PlexMetadata> _episodes = [];
bool _isLoadingEpisodes = false;
bool _watchStateChanged = false;
// Capture keyboard mode once at init to avoid rebuild dependency
bool _initialKeyboardMode = false;
/// Get the correct PlexClient for this season's server
PlexClient? _getClientForSeason(BuildContext context) {
@@ -55,6 +57,8 @@ class _SeasonDetailScreenState extends State<SeasonDetailScreen> with ItemUpdata
super.initState();
// Initialize the client once in initState
WidgetsBinding.instance.addPostFrameCallback((_) {
// Capture keyboard mode once to avoid rebuild dependency when mode changes
_initialKeyboardMode = InputModeTracker.isKeyboardMode(context);
_client = _getClientForSeason(context);
_loadEpisodes();
});
@@ -165,7 +169,7 @@ class _SeasonDetailScreenState extends State<SeasonDetailScreen> with ItemUpdata
client: _client,
isOffline: widget.isOffline,
localPosterPath: localPosterPath,
autofocus: index == 0 && InputModeTracker.isKeyboardMode(context),
autofocus: index == 0 && _initialKeyboardMode,
onTap: () async {
await navigateToVideoPlayerWithRefresh(
context,
+9 -11
View File
@@ -1266,18 +1266,16 @@ class _PlexVideoControlsState extends State<PlexVideoControls> with WindowListen
final key = event.logicalKey;
final isPlayPauseKey = _isPlayPauseKey(event);
// Handle play/pause via focus when navigation is enabled (TV/gamepad)
// When navigation is disabled, the global handler (_handleGlobalKeyEvent) handles it
if (_videoPlayerNavigationEnabled || isMobile) {
if (_isPlayPauseActivation(event)) {
widget.player.playOrPause();
_showControlsWithFocus(requestFocus: _videoPlayerNavigationEnabled);
return KeyEventResult.handled;
}
// Swallow other play/pause events (e.g., key up/repeat) to prevent focus side effects
if (isPlayPauseKey) {
return KeyEventResult.handled;
// Always consume play/pause keys to prevent propagation to background routes
// On TV/mobile, handle play/pause here; on desktop, the global handler does it
if (isPlayPauseKey) {
if (_videoPlayerNavigationEnabled || isMobile) {
if (_isPlayPauseActivation(event)) {
widget.player.playOrPause();
_showControlsWithFocus(requestFocus: _videoPlayerNavigationEnabled);
}
}
return KeyEventResult.handled;
}
// Handle Back/Escape: show controls if hidden, navigate back if visible