import React, { Component } from 'react' import { StyleSheet, View, Text, Image, TouchableWithoutFeedback, TouchableOpacity, TouchableNativeFeedbackBase, StatusBar, PanResponder, Animated, ActivityIndicator } from 'react-native' import Slider from "@react-native-community/slider" import Video from "react-native-video" import { height, isIos, px2dp, statusBarHeight, width } from '../../utils/base'; import SystemSetting from 'react-native-system-setting' import { back, navigate } from '../../NavigationService'; // import Orientations from 'react-native-orientation'; export interface Props { route?: { params: { isHorizontal: boolean videoData: any url: string } } } export interface State { paused: boolean showIcon: boolean duration: number currentTime: number sliderTime: number maximumValue: number sliderValue: number videoWidth: number videoHeight: number isRotate: boolean isChangeSlider: boolean isFastPlay: boolean animate: Animated.Value animateX: Animated.Value brightness: number leftTY: number rightTY: Animated.Value isLoad: boolean } export default class VideoView extends React.Component { constructor(props: Props | Readonly) { super(props); } componentDidMount() { let { isHorizontal, videoData } = this.props.route.params; let { videoHeight, videoWidth } = this.state; console.log("打印状态:", isHorizontal) // SystemSetting.getBrightness().then((brightness) => { // console.log('亮度是' + brightness); // this.setState({ // brightness: brightness // }) // }); // StatusBar.setHidden(true); StatusBar.setBarStyle("light-content") StatusBar.setBackgroundColor("#000") let videoH, videoW = 0 videoH = videoData && videoData.naturalSize && videoData.naturalSize.height videoW = videoData && videoData.naturalSize && videoData.naturalSize.width if (isHorizontal) { videoWidth = width * videoW / videoH videoHeight = width this.setState({ videoWidth, videoHeight, isRotate: true, }) //竖屏时、锁定为横屏 // Orientations.lockToLandscape(); return } videoHeight = width * videoH / videoW videoWidth = width this.setState({ videoWidth, videoHeight, isRotate: false, }) // Orientations.lockToPortrait(); } componentWillUnmount() { this.timer && clearTimeout(this.timer) } public readonly state: Readonly = { paused: true, showIcon: true, duration: 1,//视频时长 currentTime: 0,//当前时 sliderTime: 0, maximumValue: 1, sliderValue: 0, videoHeight: 0, videoWidth: 0, isRotate: false, isChangeSlider: false, isFastPlay: false, animate: new Animated.Value(0), animateX: new Animated.Value(0), brightness: 0, leftTY: 0, rightTY: new Animated.Value(0), isLoad: false } public showIcon = false public videoWidth = 0 public videoHeight = 0 public playerRef = null public lastOnPressTime = 0 public thisOnPressTime = 0 public timer = null public videoData = null public textWidth = px2dp(70) public pan = new Animated.ValueXY() public sliderAnimateValue = new Animated.Value(0) public lastPaused = true public bottomOpacity = new Animated.Value(1) public containerOpacity = new Animated.Value(0) panResponder = PanResponder.create({//在view onStartShouldSetPanResponder: () => true, //手势移动,激活响应    onMoveShouldSetPanResponder: (evt, gestureState) => { let { dy, dx } = gestureState; if (Math.abs(dx) > 1 && Math.abs(dx) < 200) { console.log(111) return true } else { return false } // console.log(1) // //如果手指垂直距离移动小于5,则不激活,否则激活标签的响应操作。 // // 目的是:使标签里面的点击事件能够正常使用,如果没有点击事件。可直接return true; // return Math.abs(dx) > 1 ? true : false return true }, onPanResponderMove: (e, g) => { let { sliderValue, duration, currentTime, videoWidth, paused, brightness, leftTY, isChangeSlider, isFastPlay, showIcon } = this.state; let { dy, dx } = g; if (!paused) { this.setState({ paused: true }) this.lastPaused = false } // 控制进度 if (dx > 20 && dx < videoWidth / 2 && sliderValue < 1 || dx > -videoWidth / 2 && dx < -20 && sliderValue > 0 && sliderValue <= 1) { sliderValue = dx / (videoWidth * 50) + sliderValue if (sliderValue > 1) { sliderValue = 1 } if (sliderValue < 0) { sliderValue = 0 console.log("这里", sliderValue) } currentTime = sliderValue * duration console.log("currentTime", currentTime) this.playerRef.seek(currentTime); isChangeSlider = true isFastPlay = true showIcon = true // sliderTime = "0" + Number((e * duration / 100)).toFixed(2) this.setState({ currentTime, isChangeSlider, isFastPlay, showIcon, sliderValue }) this.playerRef.seek(currentTime); } // 控制亮度 // if (dy > -this.videoHeight / 10 && dy < this.videoHeight / 2 && brightness < 1) { // console.log("到这里了1") // brightness = Math.abs(dy) / 10 + brightness // console.log("再次打印亮度", brightness) // if (brightness > 1) { // brightness = 1 // } // console.log("leftTY:", leftTY) // SystemSetting.setAppBrightness(brightness) // SystemSetting.saveBrightness(); // leftTY = leftTY + Math.abs(dy) // if (leftTY > px2dp(100)) { // leftTY = px2dp(100) // } // this.setState({ // leftTY // }) // } // if (dy > 10 && dy < this.videoHeight / 2 && brightness < 1) { // console.log("到这里了") // brightness = brightness - dy / 150 // if (brightness < 0) { // brightness = 0 // } // SystemSetting.setAppBrightness(brightness); // SystemSetting.saveBrightness(); // } }, onPanResponderRelease: (e, g) => { let { paused } = this.state; console.log("") if (!this.lastPaused) { this.timer = setTimeout(() => { this.setState({ isChangeSlider: false, showIcon: false, paused: false }) }, 1000); } else { this.timer = setTimeout(() => { this.setState({ isChangeSlider: false, showIcon: false, }) }, 1000); } } }) onShowIcon = () => { this.timer && clearTimeout(this.timer) let { paused, showIcon } = this.state; showIcon = true this.setState({ showIcon }) this.timer = setTimeout(() => { this.setState({ showIcon: !showIcon }) }, 1500); } onChangePlayStatus = () => { this.timer && clearTimeout(this.timer) let { paused, showIcon, isChangeSlider } = this.state; isChangeSlider = false // if (isFirstShowIcon) { this.setState({ paused: !paused, isChangeSlider }) this.timer = setTimeout(() => { this.setState({ showIcon: false }) }, 1500); } onValueChange = (e) => { this.timer && clearTimeout(this.timer) let { currentTime, duration, isChangeSlider, showIcon, isFastPlay } = this.state; currentTime = e * duration isChangeSlider = true isFastPlay = true showIcon = true // sliderTime = "0" + Number((e * duration / 100)).toFixed(2) this.setState({ currentTime, isChangeSlider, isFastPlay, showIcon }) this.playerRef.seek(currentTime); this.timer = setTimeout(() => { this.setState({ isChangeSlider: false, isFastPlay: false, showIcon: false }) }, 600); } showTime(val: number) { val = ~~val if (val < 60) { if (val < 10) { return "00:" + "0" + val.toFixed(0) } else { return "00:" + val.toFixed(0) } } else { var min_total = Math.floor(val / 60); // 分钟 var sec = Math.floor(val % 60); // 余秒 if (min_total < 60) { if (min_total < 10) { if (sec < 10) { return "0" + min_total + ":0" + sec.toFixed(0) } else { return "0" + min_total + ":" + sec.toFixed(0) } } else { if (sec < 10) { return min_total + ":0" + sec.toFixed(0) } else { return min_total + ":" + sec.toFixed(0) } } // return min_total + "分钟" + secStr + "秒"; } else { var hour_total = Math.floor(min_total / 60); // 小时数 var min = Math.floor(min_total % 60); // 余分钟 if (min < 10) { if (sec < 10) { return "0" + hour_total + ":0" + min + ":0" + sec.toFixed(0) } else { return hour_total + ":" + min + ":" + sec.toFixed(0) } } else { if (sec < 10) { return min + ":0" + sec.toFixed(0) } else { return min + ":" + sec.toFixed(0) } } // return hour_total + "小时" + min + "分钟" + sec + "秒"; } } } // 拖动进度条时候 // 0-1 ---》curtime时间---》显示转化 // 播放的时候 // curtime--->0-1----》显示转化 //刚加载时 onLoad = (e) => { let { duration, maximumValue, isLoad } = this.state; this.timer && clearTimeout(this.timer) duration = e && e.duration this.videoData = e maximumValue = duration Animated.sequence([ Animated.timing(this.bottomOpacity, { toValue: 0, duration: 1500, useNativeDriver: true }), Animated.timing(this.containerOpacity, { toValue: 1, duration: 500, useNativeDriver: true }) // Animated.spring(this.state.scale, { // toValue: 1, // velocity: 8,//初始速度 // friction: 4,//摩擦力值 // tension: 10,//弹跳的速度值 // useNativeDriver: true // }) ]).start() this.timer = setTimeout(() => { isLoad = true this.setState({ duration, maximumValue, isLoad }) }, 2000); } //视频播放时 onProgress = (e) => { console.log("打印进度:", e) let { currentTime, sliderTime, duration, sliderValue, paused, isChangeSlider, isFastPlay } = this.state; currentTime = e && e.currentTime sliderValue = currentTime / duration isFastPlay = false // isChangeSlider = false this.setState({ currentTime, sliderValue, isFastPlay // isChangeSlidrer }) } onEnd = () => { let { currentTime, sliderTime, duration, sliderValue, paused } = this.state; currentTime = 0, sliderValue = 0, paused = true this.playerRef.seek(currentTime); this.setState({ currentTime, sliderValue, paused }) } onAllScreen = () => { this.jumpVideoView() } jumpVideoView = () => { // Orientations.lockToPortrait(); // StatusBar.setBarStyle("dark-content") // StatusBar.setBackgroundColor("rgba(0,0,0,0)") setTimeout(() => { back() }, 300); } render() { let { paused, showIcon, maximumValue, sliderValue, videoHeight, videoWidth, isChangeSlider, isFastPlay, isLoad } = this.state; let { isHorizontal, videoData, url } = this.props.route.params; return ( { isLoad ? null : { isIos() ? : } } < Video source={{ uri: url ? url : "http://mirror.aarnet.edu.au/pub/TED-talks/911Mothers_2010W-480p.mp4", mainVer: 1, patchVer: 0 }}//在给定的扩展版本中查找.mp4文件(background.mp4). ref={c => { this.playerRef = c }} rate={1.0} //0暂停,1是正常的. volume={1.0} //0静音,1是正常的. muted={false} //完全静音. paused={paused} //完全暂停播放. resizeMode="cover" //以纵横比填充整个屏幕. repeat={false} //永远重复. onLoad={this.onLoad} onProgress={this.onProgress} // onBuffer = { this . onBuffer } // 远程视频缓冲时回调 // onError = { this . videoError } // onLoadStart={this.loadStart}//视频开始加载时的回调 // onLoad={this.setDuration} //视频加载时的回调 // onProgress={this.时刻设定} //回调每250毫秒〜与currentTime的 onEnd={this.onEnd} //播放完成时的回调 // onError={this.videoError} //视频无法加载时回调 style={[styles.backgroundVideo, { width: videoWidth, height: videoHeight, }]} /> { isLoad ? { showIcon ? : null } {this.showTime(this.state.currentTime)} {this.showTime(this.state.duration)} : } { isLoad ? { isChangeSlider ? {this.showTime(this.state.currentTime)} : null } : null } ); } } const styles = StyleSheet.create({ main: { flex: 1, justifyContent: "center", alignItems: "center", backgroundColor: "#000" // marginLeft: px2dp(12.5) // paddingTop: px2dp(100), }, backgroundVideo: { // width: width - px2dp(25), // height: px2dp(200), // backgroundColor: "red", }, overflowStyle: { // width: px2dp(32), // height: px2dp(32), justifyContent: "center", alignItems: "center", zIndex: 999, // backgroundColor: "red" // marginTop: px2dp(-200) }, iconStyle: { width: px2dp(28), height: px2dp(28), alignSelf: "center", justifyContent: "center", alignItems: "center" // marginTop: px2dp(-10) // backgroundColor: "#f6f6f6" }, sliderBox: { position: "absolute", paddingHorizontal: px2dp(10), flexDirection: "row", // alignSelf:"center" // justifyContent: "center", }, progresTextStyle: { height: px2dp(30), lineHeight: px2dp(30), alignItems: "center", color: "#f6f6f6", fontSize: 12, // backgroundColor: "blue" }, sliderStyle: { // width: width - px2dp(165), // backgroundColor: 'blue', // bottom: px2dp(10) }, miniSlider: { width: width / 3, height: px2dp(5) }, allScreenBox: { // backgroundColor: "#fff", height: px2dp(36), width: px2dp(36), justifyContent: "center", }, allScreenStyle: { width: px2dp(20), height: px2dp(18), }, overflowCurrentTimeText: { color: "#fff", textAlign: "center", fontSize: 38, zIndex: 99, opacity: 0.7, marginTop: px2dp(-120) }, lightVloumBoxStyle: { width: height, height: px2dp(240), marginBottom: px2dp(50), justifyContent: "center", // justifyContent: "space-around", alignItems: "center", flexDirection: "row", // backgroundColor: "#fff" }, leftLightStyle: { width: px2dp(10), height: px2dp(100), zIndex: 9999, // backgroundColor: "red", overflow: "hidden" }, leftLightAnimateStyle: { width: px2dp(10), height: px2dp(100), backgroundColor: "#fff" }, middleStyle: { width: height / 3, height: px2dp(240), justifyContent: "center", alignItems: "center" }, rightVloumStyle: { width: px2dp(10), height: px2dp(100), backgroundColor: "blue" }, headerIcon: { width: px2dp(20), height: px2dp(20), tintColor: '#000' }, backIcon: { position: 'absolute', width: px2dp(20), height: px2dp(20), left: px2dp(25), top: statusBarHeight / 4 } })