mirror of
https://github.com/tapframe/NuvioStreaming.git
synced 2026-04-21 16:51:57 +00:00
android player wordsplitting fix
This commit is contained in:
parent
ecaaaa66ed
commit
348cbf86d8
1 changed files with 525 additions and 530 deletions
|
|
@ -226,8 +226,8 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
const [isBackdropLoaded, setIsBackdropLoaded] = useState(false);
|
||||
const backdropImageOpacityAnim = useRef(new Animated.Value(0)).current;
|
||||
const [isBuffering, setIsBuffering] = useState(false);
|
||||
const [rnVideoAudioTracks, setRnVideoAudioTracks] = useState<Array<{id: number, name: string, language?: string}>>([]);
|
||||
const [rnVideoTextTracks, setRnVideoTextTracks] = useState<Array<{id: number, name: string, language?: string}>>([]);
|
||||
const [rnVideoAudioTracks, setRnVideoAudioTracks] = useState<Array<{ id: number, name: string, language?: string }>>([]);
|
||||
const [rnVideoTextTracks, setRnVideoTextTracks] = useState<Array<{ id: number, name: string, language?: string }>>([]);
|
||||
|
||||
// Speed boost state for hold-to-speed-up feature
|
||||
const [isSpeedBoosted, setIsSpeedBoosted] = useState(false);
|
||||
|
|
@ -323,8 +323,8 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
|
||||
|
||||
// VLC track state - will be managed by VlcVideoPlayer component
|
||||
const [vlcAudioTracks, setVlcAudioTracks] = useState<Array<{id: number, name: string, language?: string}>>([]);
|
||||
const [vlcSubtitleTracks, setVlcSubtitleTracks] = useState<Array<{id: number, name: string, language?: string}>>([]);
|
||||
const [vlcAudioTracks, setVlcAudioTracks] = useState<Array<{ id: number, name: string, language?: string }>>([]);
|
||||
const [vlcSubtitleTracks, setVlcSubtitleTracks] = useState<Array<{ id: number, name: string, language?: string }>>([]);
|
||||
const [vlcSelectedAudioTrack, setVlcSelectedAudioTrack] = useState<number | undefined>(undefined);
|
||||
const [vlcSelectedSubtitleTrack, setVlcSelectedSubtitleTrack] = useState<number | undefined>(undefined);
|
||||
const [vlcRestoreTime, setVlcRestoreTime] = useState<number | undefined>(undefined); // Time to restore after remount
|
||||
|
|
@ -629,7 +629,7 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
const shouldLoadMetadata = Boolean(id && type);
|
||||
const metadataResult = useMetadata({ id: id || 'placeholder', type: (type as any) });
|
||||
const { settings: appSettings } = useSettings();
|
||||
const { metadata, loading: metadataLoading, groupedEpisodes: metadataGroupedEpisodes, cast, loadCast } = shouldLoadMetadata ? (metadataResult as any) : { metadata: null, loading: false, groupedEpisodes: {}, cast: [], loadCast: () => {} };
|
||||
const { metadata, loading: metadataLoading, groupedEpisodes: metadataGroupedEpisodes, cast, loadCast } = shouldLoadMetadata ? (metadataResult as any) : { metadata: null, loading: false, groupedEpisodes: {}, cast: [], loadCast: () => { } };
|
||||
|
||||
// Logo animation values
|
||||
const logoScaleAnim = useRef(new Animated.Value(0.8)).current;
|
||||
|
|
@ -823,7 +823,7 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
return () => {
|
||||
if (isSpeedBoosted) {
|
||||
// best-effort restoration on unmount
|
||||
try { setPlaybackSpeed(originalSpeed); } catch {}
|
||||
try { setPlaybackSpeed(originalSpeed); } catch { }
|
||||
}
|
||||
};
|
||||
}, [isSpeedBoosted, originalSpeed]);
|
||||
|
|
@ -916,7 +916,7 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
setVlcKey(`vlc-focus-${Date.now()}`);
|
||||
}, 100);
|
||||
}
|
||||
return () => {};
|
||||
return () => { };
|
||||
}, [useVLC])
|
||||
);
|
||||
|
||||
|
|
@ -1773,10 +1773,10 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
const isTablet = Math.min(dw, dh) >= 768 || ((Platform as any).isPad === true);
|
||||
if (!isTablet) {
|
||||
setTimeout(() => {
|
||||
ScreenOrientation.lockAsync(ScreenOrientation.OrientationLock.PORTRAIT_UP).catch(() => {});
|
||||
ScreenOrientation.lockAsync(ScreenOrientation.OrientationLock.PORTRAIT_UP).catch(() => { });
|
||||
}, 50);
|
||||
} else {
|
||||
ScreenOrientation.unlockAsync().catch(() => {});
|
||||
ScreenOrientation.unlockAsync().catch(() => { });
|
||||
}
|
||||
disableImmersiveMode();
|
||||
|
||||
|
|
@ -1793,10 +1793,10 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
const isTablet = Math.min(dw, dh) >= 768 || ((Platform as any).isPad === true);
|
||||
if (!isTablet) {
|
||||
setTimeout(() => {
|
||||
ScreenOrientation.lockAsync(ScreenOrientation.OrientationLock.PORTRAIT_UP).catch(() => {});
|
||||
ScreenOrientation.lockAsync(ScreenOrientation.OrientationLock.PORTRAIT_UP).catch(() => { });
|
||||
}, 50);
|
||||
} else {
|
||||
ScreenOrientation.unlockAsync().catch(() => {});
|
||||
ScreenOrientation.unlockAsync().catch(() => { });
|
||||
}
|
||||
disableImmersiveMode();
|
||||
|
||||
|
|
@ -2334,9 +2334,9 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
try {
|
||||
const merged = { ...(saved || {}), subtitleSize: migrated };
|
||||
await storageService.saveSubtitleSettings(merged);
|
||||
} catch {}
|
||||
} catch { }
|
||||
}
|
||||
try { await mmkvStorage.removeItem(SUBTITLE_SIZE_KEY); } catch {}
|
||||
try { await mmkvStorage.removeItem(SUBTITLE_SIZE_KEY); } catch { }
|
||||
return;
|
||||
}
|
||||
// If no saved settings, use responsive default
|
||||
|
|
@ -2518,7 +2518,7 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
const textNow = cueNow ? cueNow.text : '';
|
||||
setCurrentSubtitle(textNow);
|
||||
logger.log('[AndroidVideoPlayer] currentSubtitle set immediately after apply (Android)');
|
||||
} catch {}
|
||||
} catch { }
|
||||
}
|
||||
} catch (error) {
|
||||
logger.error('[AndroidVideoPlayer] Error loading Wyzie subtitle:', error);
|
||||
|
|
@ -2834,33 +2834,28 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
|
||||
// Extract formatted segments from current cue
|
||||
if (currentCue?.formattedSegments) {
|
||||
// Split by newlines to get per-line segments
|
||||
const lines = (currentCue.text || '').split(/\r?\n/);
|
||||
const segmentsPerLine: SubtitleSegment[][] = [];
|
||||
let segmentIndex = 0;
|
||||
let currentLine: SubtitleSegment[] = [];
|
||||
|
||||
for (const line of lines) {
|
||||
const lineSegments: SubtitleSegment[] = [];
|
||||
const words = line.split(/(\s+)/);
|
||||
currentCue.formattedSegments.forEach(seg => {
|
||||
const parts = seg.text.split(/\r?\n/);
|
||||
parts.forEach((part, index) => {
|
||||
if (index > 0) {
|
||||
// New line found
|
||||
segmentsPerLine.push(currentLine);
|
||||
currentLine = [];
|
||||
}
|
||||
if (part.length > 0) {
|
||||
currentLine.push({ ...seg, text: part });
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
for (const word of words) {
|
||||
if (word.trim()) {
|
||||
if (segmentIndex < currentCue.formattedSegments.length) {
|
||||
lineSegments.push(currentCue.formattedSegments[segmentIndex]);
|
||||
segmentIndex++;
|
||||
} else {
|
||||
// Fallback if segment count doesn't match
|
||||
lineSegments.push({ text: word });
|
||||
}
|
||||
}
|
||||
if (currentLine.length > 0) {
|
||||
segmentsPerLine.push(currentLine);
|
||||
}
|
||||
|
||||
if (lineSegments.length > 0) {
|
||||
segmentsPerLine.push(lineSegments);
|
||||
}
|
||||
}
|
||||
|
||||
setCurrentFormattedSegments(segmentsPerLine.length > 0 ? segmentsPerLine : []);
|
||||
setCurrentFormattedSegments(segmentsPerLine);
|
||||
} else {
|
||||
setCurrentFormattedSegments([]);
|
||||
}
|
||||
|
|
@ -2914,8 +2909,8 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
if (typeof saved.subtitleLineHeightMultiplier === 'number') setSubtitleLineHeightMultiplier(saved.subtitleLineHeightMultiplier);
|
||||
if (typeof saved.subtitleOffsetSec === 'number') setSubtitleOffsetSec(saved.subtitleOffsetSec);
|
||||
}
|
||||
} catch {} finally {
|
||||
try { setSubtitleSettingsLoaded(true); } catch {}
|
||||
} catch { } finally {
|
||||
try { setSubtitleSettingsLoaded(true); } catch { }
|
||||
}
|
||||
})();
|
||||
}, []);
|
||||
|
|
@ -3433,7 +3428,7 @@ const AndroidVideoPlayer: React.FC = () => {
|
|||
<LinearGradient
|
||||
start={{ x: 0, y: 0.5 }}
|
||||
end={{ x: 1, y: 0.5 }}
|
||||
colors={[ 'rgba(0,0,0,0.85)', 'rgba(0,0,0,0.0)' ]}
|
||||
colors={['rgba(0,0,0,0.85)', 'rgba(0,0,0,0.0)']}
|
||||
locations={[0, 1]}
|
||||
style={StyleSheet.absoluteFill}
|
||||
/>
|
||||
|
|
|
|||
Loading…
Reference in a new issue