Приостановить видео при выходе за пределы экрана в RecyclerListView в React Native
Я реализую приложение для воспроизведения видео (например, Instagram Reels или tik tok) с помощью RecyclerListView в React-Native. При разработке приложения я столкнулся с проблемой одновременного воспроизведения всех видео в списке. Я хочу приостановить все остальные видео, которые находятся за пределами экрана, и воспроизводить их только при прокрутке к определенному видео, а видео отображается на экране.
Как это сделать? Я много чего пробовал, но не нашел решения для RecyclerListView.
Я использовал react-native-video для воспроизведения видео.
App.js
import VideoPlayer from './ViewVideo';
const fakeData = [
{
type: 'NORMAL',
item: {
uri: require('./images/likd2.mp4'),
},
},
{
type: 'NORMAL',
item: {
uri: require('./images/Linkd.mp4'),
},
},
{
type: 'NORMAL',
item: {
uri: require('./images/PlayDate.mp4'),
},
},
];
export default class Myworld extends React.Component {
dataProvider = new DataProvider((r1, r2) => {
return r1 !== r2;
}).cloneWithRows(fakeData);
layoutProvider = new LayoutProvider(
(i) => {
return this.dataProvider.getDataForIndex(i).type;
},
(type, dim) => {
switch (type) {
case 'NORMAL':
dim.width = '100%';
dim.height = '100%';
break;
default:
dim.width = '100%';
dim.height = '100%';
break;
}
},
);
rowRenderer = (type, data, index) => {
switch (type) {
case 'NORMAL':
return (
<View>
<VideoPlayer source={uri} />
</View>
);
}
};
render() {
return (
<>
<SafeAreaView style={styles.container}>
<RecyclerListView
style={styles.videolistcontainer}
rowRenderer={this.rowRenderer}
dataProvider={this.dataProvider}
layoutProvider={this.layoutProvider}
initialOffset={1}
pagingEnabled={true}
showsVerticalScrollIndicator={false}
/>
</SafeAreaView>
</>
);
}
}
const styles = StyleSheet.create({
container: {
flex: 1,
alignItems: 'center',
backgroundColor: '#14171A',
},
});
ViewVideo.js
const VideoPlayer = (props) => {
const [paused, setPause] = useState(false);
return (
<>
<TouchableOpacity
style={{height: height, width: width}}
onPress={() => setPause(!paused)}>
<Video
ref={(ref) => {
setVideoRef(ref);
}}
source={props.source}
style={styles.backgroundVideo}
resizeMode={'cover'}
onError={onError(videoRef)}
paused={paused}
onLoad={onLoad}
onProgress={onProgress}
onEnd={onEnd}
repeat={false}
rate={1.0}
volume={1.0}
muted={false}
onLayout={onVideoLayout}
/>
</TouchableOpacity>
</>
);
};
export default VideoPlayer;
const styles = StyleSheet.create({
backgroundVideo: {
position: 'absolute',
width: WP('100%'),
height: HP('100%'),
left: 0,
right: 0,
top: 0,
bottom: 0,
},
});
1 ответ
Вы можете использовать AppState или React-Native.
Он указывает на будущее состояние приложения: активное, фоновое или неактивное (только для iOS)
Пример:
import React, { useRef, useState, useEffect } from "react";
import { AppState, Text, View } from "react-native";
const AppInactiveHandleExample = () => {
const appState = useRef(AppState.currentState);
const [appStateVisible, setAppStateVisible] = useState(appState.current);
useEffect(() => {
AppState.addEventListener("change", handleAppStateChange);
// Return for clear the cache of action
return () => {
AppState.removeEventListener("change", handleAppStateChange);
};
}, []);
const handleAppStateChange = nextAppState => {
if (
appState.current.match(/inactive|background/) &&
nextAppState === "active"
) {
// Execute here your action
onAppInactive()
}
appState.current = nextAppState;
setAppStateVisible(appState.current);
};
// Action executed when app was inactive or background
const onAppInactive = () => {
// Your code here
}
return (
<View>
<Text>Current state is: {appStateVisible}</Text>
</View>
);
};
export default AppInactiveHandleExample;