How to stream and download a video using VideoView in Android

Hi there,

It’s been a while I haven’t written anything here, well was busy with my new company and consulting others!

A customer of mine wants to download and play video simultaneously at first I was confidence that  requirement is easy! But it was only a dream because android’s SDK support no such functionality for whatever reason.

But hopefully VideoView supports http streaming and it leads me to implement a HTTP internal server as a fake http streaming server and ask VideoView to get data from it!

it sound quite easy but there are loads of things that you need to take care.

1-creating a HTTP server, thanks Lord there is one for free NanoHTTPD

2-read data in chunks and send it back to VideoView

3-respond to VideoView so it could request for other chunks.

for this part you have to check if VideoView is sending request with “Range” header if not it means it is the first time so you have to response with “Content-Range: bytes 0-YOUR_CHUNK” also you have to send the “Content-Length : full length of file” so that VideoView could request back for other chunks and at the end don’t forget to send your response with “206” not with “200”.

“HTTP 206” means partial data!

4-your video files must be encoded correctly otherwise it doesn’t work at all, you can read full article here or just simply download ffmpeg and encode your video with that!

the rest is code : I just copied the useful part here, you can find the full solution in my github


    public class VideoStreamServer extends NanoHTTPD
        public VideoStreamServer(int port) {
        public Response serve(String uri, Method method, Map<String, String> headers, Map<String, String> parms, Map<String, String> files) {
            long range;
            if (headers.containsKey("range"))
                String contentRange = headers.get("range");
                range = Integer.parseInt(contentRange.substring(contentRange.indexOf("=") + 1, contentRange.indexOf("-")));
                range = 0;
            byte[] buffer;
            int constantLength = 256000;
            long bufLength=0;
            boolean isLastPart=false;
            try {
                RandomAccessFile ff =new RandomAccessFile(new File("/mnt/sdcard","1.mp4"),"rw" );
                long remainingChunk = ff.length() - range; //remaining
                if (remainingChunk < constantLength){
                    bufLength= remainingChunk; //means last part
                    isLastPart = true;
                    bufLength = constantLength;
                if (range !=0)
                buffer= new byte[(int)bufLength];
            } catch (FileNotFoundException e) {
                buffer = new byte[0];
            } catch (IOException e) {
                buffer = new byte[0];
            Response response;
                response = new Response(Response.Status.PARTIAL_CONTENT,"video/mp4",new ByteArrayInputStream(buffer));
            response.addHeader("Content-Range",String.format("bytes %s-%s/%s", range,(range+bufLength),"891064"));
            Log.e("SERVER","Inside server sent " + String.format("bytes %s-%s/%s", range,(range+bufLength),"891064"));
            return response;