Files

125 lines
3.3 KiB
Dart
Raw Permalink Normal View History

2026-07-14 11:11:36 +08:00
import 'package:flutter/foundation.dart';
import '../../../core/contracts/playback.dart';
import '../../../providers/subtitle_settings_provider.dart';
enum InitialSubtitleSelectionType { unchanged, disabled, track }
class InitialSubtitleSelection {
final InitialSubtitleSelectionType type;
final EmbySubtitleTrack? track;
const InitialSubtitleSelection._({required this.type, this.track});
static const unchanged = InitialSubtitleSelection._(
type: InitialSubtitleSelectionType.unchanged,
);
static const disabled = InitialSubtitleSelection._(
type: InitialSubtitleSelectionType.disabled,
);
const InitialSubtitleSelection.track(EmbySubtitleTrack selectedTrack)
: this._(type: InitialSubtitleSelectionType.track, track: selectedTrack);
}
InitialSubtitleSelection resolveInitialSubtitleSelection({
required List<EmbySubtitleTrack> subtitles,
required int? preferredSubtitleStreamIndex,
required int? defaultSubtitleStreamIndex,
required RememberedSubtitleTrack? rememberedSubtitle,
}) {
if (preferredSubtitleStreamIndex != null &&
preferredSubtitleStreamIndex >= 0) {
return _selectionForStreamIndex(subtitles, preferredSubtitleStreamIndex);
}
if (rememberedSubtitle != null) {
if (rememberedSubtitle.isNone) {
return InitialSubtitleSelection.disabled;
}
final rememberedStreamIndex = matchRememberedSubtitle(
rememberedSubtitle,
subtitles,
);
if (rememberedStreamIndex != null) {
return _selectionForStreamIndex(subtitles, rememberedStreamIndex);
}
}
if (preferredSubtitleStreamIndex != null &&
preferredSubtitleStreamIndex < 0) {
return InitialSubtitleSelection.disabled;
}
if (defaultSubtitleStreamIndex != null && defaultSubtitleStreamIndex >= 0) {
return _selectionForStreamIndex(subtitles, defaultSubtitleStreamIndex);
}
if (defaultSubtitleStreamIndex == -1) {
return InitialSubtitleSelection.disabled;
}
return InitialSubtitleSelection.unchanged;
}
InitialSubtitleSelection _selectionForStreamIndex(
List<EmbySubtitleTrack> subtitles,
int streamIndex,
) {
final selectedTrack = subtitles
.where((subtitle) => subtitle.index == streamIndex)
.firstOrNull;
return selectedTrack == null
? InitialSubtitleSelection.unchanged
: InitialSubtitleSelection.track(selectedTrack);
}
@visibleForTesting
int? matchRememberedSubtitle(
RememberedSubtitleTrack remembered,
List<EmbySubtitleTrack> subtitles,
) {
if (subtitles.isEmpty) return null;
final wantedLanguage = remembered.language?.toLowerCase();
final wantedTitle = remembered.title?.toLowerCase();
if (wantedLanguage != null && wantedTitle != null) {
for (final subtitle in subtitles) {
if (subtitle.language?.toLowerCase() == wantedLanguage &&
subtitle.title?.toLowerCase() == wantedTitle) {
return subtitle.index;
}
}
}
if (wantedTitle != null) {
for (final subtitle in subtitles) {
if (subtitle.title?.toLowerCase() == wantedTitle) {
return subtitle.index;
}
}
}
if (wantedLanguage != null) {
for (final subtitle in subtitles) {
if (subtitle.language?.toLowerCase() == wantedLanguage) {
return subtitle.index;
}
}
}
for (final subtitle in subtitles) {
if (subtitle.index == remembered.streamIndex) {
return subtitle.index;
}
}
return null;
}