Basic example
Here’s a complete example to get you started with React Native Video. This example shows a simple video player with native controls:
import React from 'react' ;
import { StyleSheet , View } from 'react-native' ;
import { useVideoPlayer , VideoView } from 'react-native-video' ;
export default function App () {
const player = useVideoPlayer (
'https://www.w3schools.com/html/mov_bbb.mp4' ,
( player ) => {
player . play ();
}
);
return (
< View style = { styles . container } >
< VideoView
player = { player }
style = { styles . video }
controls
/>
</ View >
);
}
const styles = StyleSheet . create ({
container: {
flex: 1 ,
justifyContent: 'center' ,
alignItems: 'center' ,
},
video: {
width: '100%' ,
aspectRatio: 16 / 9 ,
},
});
The useVideoPlayer hook creates and manages a video player instance. The second parameter is a setup function that runs when the player is ready.
Understanding the code
Let’s break down the key components:
Import the components
Import useVideoPlayer and VideoView from react-native-video: import { useVideoPlayer , VideoView } from 'react-native-video' ;
Create a player with useVideoPlayer
The useVideoPlayer hook creates a player instance with a video source: const player = useVideoPlayer (
'https://www.w3schools.com/html/mov_bbb.mp4' ,
( player ) => {
player . play (); // Auto-play when ready
}
);
First parameter: The video source (URL or local file)
Second parameter: Setup function called when the player loads
Render VideoView
The VideoView component displays the video: < VideoView
player = { player }
style = { styles . video }
controls
/>
player: The player instance from useVideoPlayer
style: Standard React Native style prop
controls: Show native playback controls
Playing local videos
You can play videos from your app’s assets using require():
const player = useVideoPlayer (
require ( './assets/video.mp4' ),
( player ) => {
player . play ();
}
);
Controlling playback
The player instance provides methods and properties to control playback:
Play/Pause
Seeking
Volume and Mute
Playback Rate
const player = useVideoPlayer ( videoSource );
// Play the video
player . play ();
// Pause the video
player . pause ();
// Check if playing
const isPlaying = player . isPlaying ;
Handling events
Use the useEvent hook to listen to player events:
import { useVideoPlayer , VideoView , useEvent } from 'react-native-video' ;
export default function App () {
const player = useVideoPlayer ( videoSource );
useEvent ( player , 'onLoad' , ( data ) => {
console . log ( 'Video loaded:' , data );
});
useEvent ( player , 'onProgress' , ( data ) => {
console . log ( 'Current time:' , data . currentTime );
});
useEvent ( player , 'onEnd' , () => {
console . log ( 'Video ended' );
});
useEvent ( player , 'onError' , ( error ) => {
console . error ( 'Video error:' , error );
});
return < VideoView player = { player } style = { styles . video } /> ;
}
The useEvent hook automatically manages event subscriptions and cleans them up when the component unmounts.
Complete example with controls
Here’s a more complete example with custom controls:
import React , { useState } from 'react' ;
import { StyleSheet , View , Button , Text } from 'react-native' ;
import { useVideoPlayer , VideoView , useEvent } from 'react-native-video' ;
export default function App () {
const [ currentTime , setCurrentTime ] = useState ( 0 );
const [ duration , setDuration ] = useState ( 0 );
const player = useVideoPlayer (
'https://www.w3schools.com/html/mov_bbb.mp4' ,
( player ) => {
player . loop = true ;
player . play ();
}
);
useEvent ( player , 'onProgress' , ( data ) => {
setCurrentTime ( data . currentTime );
});
useEvent ( player , 'onLoad' , ( data ) => {
setDuration ( player . duration );
});
const formatTime = ( seconds : number ) => {
const mins = Math . floor ( seconds / 60 );
const secs = Math . floor ( seconds % 60 );
return ` ${ mins } : ${ secs . toString (). padStart ( 2 , '0' ) } ` ;
};
return (
< View style = { styles . container } >
< VideoView
player = { player }
style = { styles . video }
resizeMode = "contain"
/>
< View style = { styles . controls } >
< Text style = { styles . time } >
{ formatTime ( currentTime ) } / { formatTime ( duration ) }
</ Text >
< View style = { styles . buttons } >
< Button
title = "⏮️ -10s"
onPress = { () => player . seekBy ( - 10 ) }
/>
< Button
title = { player . isPlaying ? '⏸️ Pause' : '▶️ Play' }
onPress = { () => player . isPlaying ? player . pause () : player . play () }
/>
< Button
title = "⏭️ +10s"
onPress = { () => player . seekBy ( 10 ) }
/>
</ View >
</ View >
</ View >
);
}
const styles = StyleSheet . create ({
container: {
flex: 1 ,
justifyContent: 'center' ,
},
video: {
width: '100%' ,
aspectRatio: 16 / 9 ,
},
controls: {
padding: 16 ,
},
time: {
textAlign: 'center' ,
fontSize: 16 ,
marginBottom: 16 ,
},
buttons: {
flexDirection: 'row' ,
justifyContent: 'space-around' ,
},
});
Video configuration
For more advanced scenarios, pass a configuration object instead of a URL:
import type { VideoConfig } from 'react-native-video' ;
const videoConfig : VideoConfig = {
uri: 'https://example.com/video.m3u8' ,
headers: {
'Authorization' : 'Bearer token123' ,
},
externalSubtitles: [
{
uri: 'https://example.com/subtitles_en.vtt' ,
label: 'English' ,
language: 'en' ,
type: 'vtt' ,
},
],
};
const player = useVideoPlayer ( videoConfig , ( player ) => {
player . play ();
});
Video configuration supports headers, DRM parameters, buffer config, metadata, and external subtitles. See the VideoConfig API reference for all options.
Common customizations
Resize modes
Control how the video fits within the view:
< VideoView
player = { player }
style = { styles . video }
resizeMode = "contain" // 'contain' | 'cover' | 'stretch' | 'none'
/>
contain : Fit video within view, maintaining aspect ratio (may show letterboxing)
cover : Fill entire view, maintaining aspect ratio (may crop)
stretch : Fill entire view, ignoring aspect ratio
none : Use video’s native size
Background playback
Enable playback when the app is in the background:
const player = useVideoPlayer ( videoSource , ( player ) => {
player . playInBackground = true ;
player . play ();
});
Picture in Picture
Enable Picture in Picture mode:
import { useRef } from 'react' ;
import type { VideoViewRef } from 'react-native-video' ;
const videoRef = useRef < VideoViewRef >( null );
// Enable PiP button in controls
< VideoView
ref = { videoRef }
player = { player }
style = { styles . video }
pictureInPicture
controls
/>
// Or programmatically enter PiP
videoRef . current ?. enterPictureInPicture ();
Next steps
VideoPlayer API Learn about all player properties and methods
VideoView API Explore VideoView props and customization options
Events Handle player events and track playback state
Streaming Play HLS and DASH streams