replay musics

This commit is contained in:
2025-11-03 14:01:35 +01:00
parent 460c91f1e6
commit 94a1f1ab16
7 changed files with 143 additions and 27 deletions
+47
View File
@@ -1,4 +1,6 @@
import { Feather } from "@expo/vector-icons";
import useTrackController from "../../hooks/useTrackController";
import usePlayer from "../../hooks/usePlayer";
import { Image as ExpoImage } from "expo-image";
import React, { useCallback, useEffect, useMemo, useRef, useState } from "react";
import {
@@ -58,6 +60,7 @@ const MusicDetails = ({ route }) => {
const incrementDoneRef = useRef(false);
const timerRef = useRef(null);
const hasAutoPlayedRef = useRef(false);
const { isLooping, setLooping } = usePlayer() || {};
const { data: project } = useDataFromRef({
ref: projectId ? projectsRef.doc(projectId) : null,
@@ -193,6 +196,7 @@ const MusicDetails = ({ route }) => {
seekTo: seekTrackTo,
seekBy: seekTrackBy,
} = useTrackController(trackDescriptor);
const loopEnabled = isCurrentTrack && !!isLooping;
// Karaoke aligned words (from timestamps)
const alignedWords = useMemo(() => {
@@ -325,6 +329,31 @@ const MusicDetails = ({ route }) => {
[durationMs, trackDescriptor, isCurrentTrack, ensureLoaded, seekTrackTo]
);
const handleToggleLoop = useCallback(async () => {
if (!isCurrentTrack) return;
const next = !loopEnabled;
if (typeof setLooping === "function") {
setLooping(next);
}
if (next) {
try {
await seekTrackTo(0);
if (!isTrackPlaying) {
await resumeTrack();
}
} catch (e) {
console.log("MusicDetails loop toggle error", e?.message);
}
}
}, [
isCurrentTrack,
loopEnabled,
setLooping,
seekTrackTo,
isTrackPlaying,
resumeTrack,
]);
useEffect(() => {
if (!autoPlayRequested || hasAutoPlayedRef.current) return;
if (!trackDescriptor || !songUrl) return;
@@ -746,6 +775,24 @@ const MusicDetails = ({ route }) => {
<Text style={styles.name}>{artist}</Text>
</View>
<View style={{ ...Style.containerRow, gap: 16 }}>
<PressableScale
onPress={handleToggleLoop}
disabled={!isCurrentTrack}
hitSlop={10}
style={{
...size({ size: 32 }),
alignItems: "center",
justifyContent: "center",
opacity: isCurrentTrack ? 1 : 0.4,
}}
contentStyle={{ alignItems: "center", justifyContent: "center" }}
>
<Feather
name="repeat"
size={24}
color={loopEnabled ? Palette.primary : Palette.white}
/>
</PressableScale>
<PressableScale
onPress={async () => {
if (!projectId || !currentUID) return;