mirror of
https://github.com/tapframe/NuvioStreaming.git
synced 2026-01-11 20:10:25 +00:00
fix: fixed autoplay stream
This commit is contained in:
parent
031c0c8772
commit
01a041aebf
10 changed files with 72 additions and 84 deletions
|
|
@ -1604,22 +1604,26 @@ export const useMetadata = ({ id, type, addonId }: UseMetadataProps): UseMetadat
|
|||
});
|
||||
|
||||
// Add local scrapers if enabled
|
||||
localScrapers.filter((scraper: ScraperInfo) => scraper.enabled).forEach((scraper: ScraperInfo) => {
|
||||
initialStatuses.push({
|
||||
id: scraper.id,
|
||||
name: scraper.name,
|
||||
isLoading: true,
|
||||
hasCompleted: false,
|
||||
error: null,
|
||||
startTime: Date.now(),
|
||||
endTime: null
|
||||
const currentSettings = await mmkvStorage.getItem('app_settings');
|
||||
const enableLocalScrapersNow = currentSettings ? JSON.parse(currentSettings).enableLocalScrapers !== false : true;
|
||||
|
||||
if (enableLocalScrapersNow) {
|
||||
localScrapers.filter((scraper: ScraperInfo) => scraper.enabled).forEach((scraper: ScraperInfo) => {
|
||||
initialStatuses.push({
|
||||
id: scraper.id,
|
||||
name: scraper.name,
|
||||
isLoading: true,
|
||||
hasCompleted: false,
|
||||
error: null,
|
||||
startTime: Date.now(),
|
||||
endTime: null
|
||||
});
|
||||
initialActiveFetching.push(scraper.name);
|
||||
});
|
||||
initialActiveFetching.push(scraper.name);
|
||||
});
|
||||
}
|
||||
|
||||
setScraperStatuses(initialStatuses);
|
||||
setActiveFetchingScrapers(initialActiveFetching);
|
||||
console.log('🔍 [loadStreams] Initialized activeFetchingScrapers:', initialActiveFetching);
|
||||
|
||||
// If no scrapers are available, stop loading immediately
|
||||
if (initialStatuses.length === 0) {
|
||||
|
|
@ -1740,23 +1744,27 @@ export const useMetadata = ({ id, type, addonId }: UseMetadataProps): UseMetadat
|
|||
initialActiveFetching.push(addon.name);
|
||||
});
|
||||
|
||||
// Add local scrapers if enabled
|
||||
localScrapers.filter((scraper: ScraperInfo) => scraper.enabled).forEach((scraper: ScraperInfo) => {
|
||||
initialStatuses.push({
|
||||
id: scraper.id,
|
||||
name: scraper.name,
|
||||
isLoading: true,
|
||||
hasCompleted: false,
|
||||
error: null,
|
||||
startTime: Date.now(),
|
||||
endTime: null
|
||||
// Add local scrapers if enabled (read from storage to avoid stale closure)
|
||||
const currentSettings = await mmkvStorage.getItem('app_settings');
|
||||
const enableLocalScrapersNow = currentSettings ? JSON.parse(currentSettings).enableLocalScrapers !== false : true;
|
||||
|
||||
if (enableLocalScrapersNow) {
|
||||
localScrapers.filter((scraper: ScraperInfo) => scraper.enabled).forEach((scraper: ScraperInfo) => {
|
||||
initialStatuses.push({
|
||||
id: scraper.id,
|
||||
name: scraper.name,
|
||||
isLoading: true,
|
||||
hasCompleted: false,
|
||||
error: null,
|
||||
startTime: Date.now(),
|
||||
endTime: null
|
||||
});
|
||||
initialActiveFetching.push(scraper.name);
|
||||
});
|
||||
initialActiveFetching.push(scraper.name);
|
||||
});
|
||||
}
|
||||
|
||||
setScraperStatuses(initialStatuses);
|
||||
setActiveFetchingScrapers(initialActiveFetching);
|
||||
console.log('🔍 [loadEpisodeStreams] Initialized activeFetchingScrapers:', initialActiveFetching);
|
||||
|
||||
// If no scrapers are available, stop loading immediately
|
||||
if (initialStatuses.length === 0) {
|
||||
|
|
|
|||
|
|
@ -1090,8 +1090,8 @@
|
|||
"external_title": "مشغل خارجي",
|
||||
"external_desc": "فتح البثوث في مشغل الفيديو المفضل لديك",
|
||||
"section_playback": "خيارات التشغيل",
|
||||
"autoplay_title": "تشغيل أفضل بث تلقائياً",
|
||||
"autoplay_desc": "بدء أعلى جودة بث متاحة تلقائياً.",
|
||||
"autoplay_title": "تشغيل أول بث تلقائياً",
|
||||
"autoplay_desc": "بدء أول بث معروض في القائمة تلقائياً.",
|
||||
"resume_title": "استكمال دائماً",
|
||||
"resume_desc": "تخطي مطالبة الاستكمال والمتابعة تلقائياً من حيث توقفت (إذا تمت مشاهدة أقل من 85%).",
|
||||
"engine_title": "محرك مشغل الفيديو",
|
||||
|
|
|
|||
|
|
@ -1093,8 +1093,8 @@
|
|||
"external_title": "External Player",
|
||||
"external_desc": "Open streams in your preferred video player",
|
||||
"section_playback": "PLAYBACK OPTIONS",
|
||||
"autoplay_title": "Auto-play Best Stream",
|
||||
"autoplay_desc": "Automatically start the highest quality stream available.",
|
||||
"autoplay_title": "Auto-play First Stream",
|
||||
"autoplay_desc": "Automatically start the first stream shown in the list.",
|
||||
"resume_title": "Always Resume",
|
||||
"resume_desc": "Skip the resume prompt and automatically continue where you left off (if less than 85% watched).",
|
||||
"engine_title": "Video Player Engine",
|
||||
|
|
|
|||
|
|
@ -1090,8 +1090,8 @@
|
|||
"external_title": "Reproductor externo",
|
||||
"external_desc": "Abrir fuentes en tu reproductor de video preferido",
|
||||
"section_playback": "OPCIONES DE REPRODUCCIÓN",
|
||||
"autoplay_title": "Autorreproducir la mejor fuente",
|
||||
"autoplay_desc": "Iniciar automáticamente la fuente de mayor calidad disponible.",
|
||||
"autoplay_title": "Autorreproducir la primera fuente",
|
||||
"autoplay_desc": "Iniciar automáticamente la primera fuente mostrada en la lista.",
|
||||
"resume_title": "Reanudar siempre",
|
||||
"resume_desc": "Saltar el aviso de reanudar y continuar automáticamente donde lo dejaste (si se ha visto menos del 85%).",
|
||||
"engine_title": "Motor del reproductor",
|
||||
|
|
|
|||
|
|
@ -1090,8 +1090,8 @@
|
|||
"external_title": "Lecteur externe",
|
||||
"external_desc": "Ouvrir les flux dans votre lecteur vidéo préféré",
|
||||
"section_playback": "OPTIONS DE LECTURE",
|
||||
"autoplay_title": "Lecture automatique du meilleur flux",
|
||||
"autoplay_desc": "Démarrer automatiquement le flux de la plus haute qualité disponible.",
|
||||
"autoplay_title": "Lecture automatique du premier flux",
|
||||
"autoplay_desc": "Démarrer automatiquement le premier flux affiché dans la liste.",
|
||||
"resume_title": "Toujours reprendre",
|
||||
"resume_desc": "Passer l'invite de reprise et continuer automatiquement là où vous vous étiez arrêté (si moins de 85% vus).",
|
||||
"engine_title": "Moteur du lecteur vidéo",
|
||||
|
|
|
|||
|
|
@ -1090,8 +1090,8 @@
|
|||
"external_title": "Player Esterno",
|
||||
"external_desc": "Apri gli stream nel tuo video player preferito",
|
||||
"section_playback": "OPZIONI RIPRODUZIONE",
|
||||
"autoplay_title": "Auto-play Miglior Stream",
|
||||
"autoplay_desc": "Avvia automaticamente lo stream alla massima qualità disponibile.",
|
||||
"autoplay_title": "Auto-play Primo Stream",
|
||||
"autoplay_desc": "Avvia automaticamente il primo stream mostrato nella lista.",
|
||||
"resume_title": "Riprendi Sempre",
|
||||
"resume_desc": "Salta la richiesta di ripresa e continua automaticamente da dove avevi interrotto (se visto meno dell'85%).",
|
||||
"engine_title": "Motore Video Player",
|
||||
|
|
|
|||
|
|
@ -981,8 +981,8 @@
|
|||
"external_title": "Player Externo",
|
||||
"external_desc": "Abrir streams no seu player de vídeo preferido",
|
||||
"section_playback": "OPÇÕES DE REPRODUÇÃO",
|
||||
"autoplay_title": "Reprodução Automática (Melhor Stream)",
|
||||
"autoplay_desc": "Iniciar automaticamente o stream de melhor qualidade disponível.",
|
||||
"autoplay_title": "Reprodução Automática (Primeiro Stream)",
|
||||
"autoplay_desc": "Iniciar automaticamente o primeiro stream mostrado na lista.",
|
||||
"resume_title": "Sempre Retomar",
|
||||
"resume_desc": "Pular o aviso de retomar e continuar automaticamente de onde parou (se assistido menos de 85%).",
|
||||
"engine_title": "Motor do Player de Vídeo",
|
||||
|
|
|
|||
|
|
@ -981,8 +981,8 @@
|
|||
"external_title": "Reprodutor Externo",
|
||||
"external_desc": "Abrir streams no teu reprodutor de vídeo preferido",
|
||||
"section_playback": "OPÇÕES DE REPRODUÇÃO",
|
||||
"autoplay_title": "Reprodução Automática (Melhor Stream)",
|
||||
"autoplay_desc": "Iniciar automaticamente o stream de melhor qualidade disponível.",
|
||||
"autoplay_title": "Reprodução Automática (Primeiro Stream)",
|
||||
"autoplay_desc": "Iniciar automaticamente o primeiro stream mostrado na lista.",
|
||||
"resume_title": "Sempre Retomar",
|
||||
"resume_desc": "Saltar o aviso de retomar e continuar automaticamente de onde parou (se assistido menos de 85%).",
|
||||
"engine_title": "Motor do reprodutor",
|
||||
|
|
|
|||
|
|
@ -294,48 +294,14 @@ const PlayerSettingsScreen: React.FC = () => {
|
|||
<Switch
|
||||
value={settings.autoplayBestStream}
|
||||
onValueChange={(value) => updateSetting('autoplayBestStream', value)}
|
||||
thumbColor={settings.autoplayBestStream ? currentTheme.colors.primary : undefined}
|
||||
trackColor={{ false: '#767577', true: currentTheme.colors.primary }}
|
||||
thumbColor={settings.autoplayBestStream ? '#ffffff' : '#f4f3f4'}
|
||||
ios_backgroundColor="#3e3e3e"
|
||||
/>
|
||||
</View>
|
||||
</View>
|
||||
|
||||
<View style={styles.settingItem}>
|
||||
<View style={styles.settingContent}>
|
||||
<View style={[
|
||||
styles.settingIconContainer,
|
||||
{ backgroundColor: 'rgba(255,255,255,0.1)' }
|
||||
]}>
|
||||
<MaterialIcons
|
||||
name="restore"
|
||||
size={20}
|
||||
color={currentTheme.colors.primary}
|
||||
/>
|
||||
</View>
|
||||
<View style={styles.settingText}>
|
||||
<Text
|
||||
style={[
|
||||
styles.settingTitle,
|
||||
{ color: currentTheme.colors.text },
|
||||
]}
|
||||
>
|
||||
{t('player.resume_title')}
|
||||
</Text>
|
||||
<Text
|
||||
style={[
|
||||
styles.settingDescription,
|
||||
{ color: currentTheme.colors.textMuted },
|
||||
]}
|
||||
>
|
||||
{t('player.resume_desc')}
|
||||
</Text>
|
||||
</View>
|
||||
<Switch
|
||||
value={settings.alwaysResume}
|
||||
onValueChange={(value) => updateSetting('alwaysResume', value)}
|
||||
thumbColor={settings.alwaysResume ? currentTheme.colors.primary : undefined}
|
||||
/>
|
||||
</View>
|
||||
</View>
|
||||
|
||||
|
||||
{/* Video Player Engine for Android */}
|
||||
{Platform.OS === 'android' && !settings.useExternalPlayer && (
|
||||
|
|
|
|||
|
|
@ -48,7 +48,7 @@ export const useStreamsScreen = () => {
|
|||
const route = useRoute<RouteProp<RootStackParamList, 'Streams'>>();
|
||||
const navigation = useNavigation<RootStackNavigationProp>();
|
||||
const { id, type, episodeId, episodeThumbnail, fromPlayer } = route.params;
|
||||
const { settings } = useSettings();
|
||||
const { settings, isLoaded: settingsLoaded } = useSettings();
|
||||
const { currentTheme } = useTheme();
|
||||
const { colors } = currentTheme;
|
||||
const { pauseTrailer, resumeTrailer } = useTrailer();
|
||||
|
|
@ -586,6 +586,16 @@ export const useStreamsScreen = () => {
|
|||
setAutoplayTriggered(false);
|
||||
}, [selectedEpisode]);
|
||||
|
||||
// Initialize autoplay waiting state when settings are loaded
|
||||
// This runs after settings are fully loaded to avoid race conditions
|
||||
useEffect(() => {
|
||||
if (!settingsLoaded) return; // Wait for settings to load
|
||||
|
||||
if (settings.autoplayBestStream && !fromPlayer && !autoplayTriggered) {
|
||||
setIsAutoplayWaiting(true);
|
||||
}
|
||||
}, [settingsLoaded, settings.autoplayBestStream, fromPlayer, autoplayTriggered]);
|
||||
|
||||
// Reset provider if no longer available
|
||||
useEffect(() => {
|
||||
const isSpecialFilter =
|
||||
|
|
@ -659,11 +669,7 @@ export const useStreamsScreen = () => {
|
|||
}
|
||||
|
||||
setAutoplayTriggered(false);
|
||||
if (settings.autoplayBestStream && !fromPlayer) {
|
||||
setIsAutoplayWaiting(true);
|
||||
} else {
|
||||
setIsAutoplayWaiting(false);
|
||||
}
|
||||
// Note: isAutoplayWaiting is now handled by a separate effect that waits for settings to load
|
||||
}
|
||||
} finally {
|
||||
isLoadingStreamsRef.current = false;
|
||||
|
|
@ -678,6 +684,8 @@ export const useStreamsScreen = () => {
|
|||
useEffect(() => {
|
||||
if (settings.autoplayBestStream && !autoplayTriggered && isAutoplayWaiting) {
|
||||
const streams = selectedEpisode ? episodeStreams : groupedStreams;
|
||||
const hasLoadingStarted = streamsLoadStart !== null;
|
||||
const isStillLoading = !hasLoadingStarted || loadingStreams || loadingEpisodeStreams || activeFetchingScrapers.length > 0;
|
||||
|
||||
if (Object.keys(streams).length > 0) {
|
||||
const bestStream = getBestStream(streams);
|
||||
|
|
@ -687,9 +695,11 @@ export const useStreamsScreen = () => {
|
|||
setAutoplayTriggered(true);
|
||||
setIsAutoplayWaiting(false);
|
||||
handleStreamPress(bestStream);
|
||||
} else {
|
||||
} else if (!isStillLoading) {
|
||||
setIsAutoplayWaiting(false);
|
||||
}
|
||||
} else if (!isStillLoading) {
|
||||
setIsAutoplayWaiting(false);
|
||||
}
|
||||
}
|
||||
}, [
|
||||
|
|
@ -703,6 +713,10 @@ export const useStreamsScreen = () => {
|
|||
handleStreamPress,
|
||||
metadata,
|
||||
selectedEpisode,
|
||||
loadingStreams,
|
||||
loadingEpisodeStreams,
|
||||
activeFetchingScrapers.length,
|
||||
streamsLoadStart,
|
||||
]);
|
||||
|
||||
// Cleanup on unmount
|
||||
|
|
|
|||
Loading…
Reference in a new issue