Preface
This chapter provides a very practical function-download online videos. We also need to think about the product design and how to better integrate the newly added functions into existing products when it comes to multithreading, thread update, and other technologies, it's not just a simple interface. You are welcome to discuss product design and technical details!
StatementWelcome to repost, but please keep the original source of the article :) blog Park: http://www.cnblogs.com farmer UNCLE: http://over140.cnblogs.com
Series1. Use Vitamio to build your Android universal player (1) -- Preparation 2. Use Vitamio to build your Android universal player (2) -- gesture control brightness, volume, scaling 3. Use Vitamio to create your own Android universal player (3)-local playback (main interface, video List)
4. Use Vitamio to create your Android universal player (4)-local playback (quick search and data storage)
5. Use Vitamio to build your Android universal player (5)-Online playback (playing Youku videos)
6. Use Vitamio to create your Android universal player (6)-Online playback (playlist)
BodyI. Objectives
This chapter implements the video download function.
Usage: the online video is displayed. When you click play, a selection box is displayed asking whether to play or download the video. After you click Download, the progress bar is displayed at the top of the local video. If you want to download the video while watching it, click the video that is being downloaded in the local playback list.
II. Implementation (some major implementation code) FileDownloadHelperpublic class FileDownloadHelper {
Private static final String TAG = "FileDownloadHelper ";
/** Thread pool */
Private ThreadPool mPool = new ThreadPool ();
/** Start download */
Public static final int MESSAGE_START = 0;
/** Update progress */
Public static final int MESSAGE_PROGRESS = 1;
/** Download ended */
Public static final int MESSAGE_STOP = 2;
/** Download Error */
Public static final int MESSAGE_ERROR = 3;
/** Termination in the middle */
Private volatile boolean mIsStop = false;
Private Handler mHandler;
Public volatile HashMap <String, String> mDownloadUrls = new HashMap <String, String> ();
Public FileDownloadHelper (Handler handler ){
If (handler = null)
Throw new IllegalArgumentException ("handler cannot be blank! ");
This. mHandler = handler;
}
Public void stopALl (){
MIsStop = true;
MPool. stop ();
}
Public void newDownloadFile (final String url ){
NewDownloadFile (url, Environment. getExternalStorageDirectory () + "/" + FileUtils. getUrlFileName (url ));
}
/**
* Download a new file
*
* @ Param url
* @ Param savePath
*/
Public void newDownloadFile (final String url, final String savePath ){
If (mDownloadUrls. containsKey (url ))
Return;
Else
MDownloadUrls. put (url, savePath );
MPool. start (new Runnable (){
@ Override
Public void run (){
MHandler. sendMessage (mHandler. obtainMessage (MESSAGE_START, url ));
HttpClient client = new DefaultHttpClient ();
HttpGet = new HttpGet (url );
InputStream inputStream = null;
FileOutputStream outputStream = null;
Try {
HttpResponse response = client.exe cute (get );
HttpEntity entity = response. getEntity ();
Final int size = (int) entity. getContentLength ();
InputStream = entity. getContent ();
If (size> 0 & inputStream! = Null ){
OutputStream = new FileOutputStream (savePath );
Int ch =-1;
Byte [] buf = new byte [1, 1024];
// Update progress every second
New Timer (). schedule (new TimerTask (){
@ Override
Public void run (){
Try {
FileInputStream FCM = new FileInputStream (new File (savePath ));
Int downloadedSize = FS. available ();
If (downloadedSize> = size)
Cancel ();
MHandler. sendMessage (mHandler. obtainMessage (MESSAGE_PROGRESS, downloadedSize, size, url ));
} Catch (Exception e ){
}
}
}, 50,100 0 );
While (ch = inputStream. read (buf ))! =-1 &&! MIsStop ){
OutputStream. write (buf, 0, ch );
}
OutputStream. flush ();
}
} Catch (Exception e ){
Log. e (TAG, e. getMessage (), e );
MHandler. sendMessage (mHandler. obtainMessage (MESSAGE_ERROR, url + ":" + e. getMessage ()));
} Finally {
Try {
If (outputStream! = Null)
OutputStream. close ();
} Catch (IOException ex ){
}
Try {
If (inputStream! = Null)
InputStream. close ();
} Catch (IOException ex ){
}
}
MDownloadUrls. remove (url );
MHandler. sendMessage (mHandler. obtainMessage (MESSAGE_STOP, url ));
}
});
}
}
Code Description: a. ThreadPool is a thread pool. Refer to the project code.
B. here we use Time timing to fl the progress, instead of directly updating the progress when writing data. This is because the write per second is high, the UI is updated too frequently, and may cause timeout and other problems.
Handle
Public Handler mDownloadHandler = new Handler (){
@ Override
Public void handleMessage (Message msg ){
PFile p;
String url = msg. obj. toString ();
Switch (msg. what ){
Case FileDownloadHelper. MESSAGE_START: // start download
P = new PFile ();
P. path = mParent. mFileDownload. mDownloadUrls. get (url );
P. title = new File (p. path). getName ();
P. status = 0;
P. file_size = 0;
If (mDownloadAdapter = null ){
MDownloadAdapter = new FileAdapter (getActivity (), new ArrayList <PFile> ());
MDownloadAdapter. add (p, url );
MTempListView. setAdapter (mDownloadAdapter );
MTempListView. setVisibility (View. VISIBLE );
} Else {
MDownloadAdapter. add (p, url );
MDownloadAdapter. notifyDataSetChanged ();
}
Break;
Case FileDownloadHelper. MESSAGE_PROGRESS: // download
P = mDownloadAdapter. getItem (url );
P. temp_file_size = msg. arg1;
P. file_size = msg. arg2;
Int status = (int) (msg. arg1 * 1.0/msg. arg2) * 10 );
If (status> 10)
Status = 10;
P. status = status;
MDownloadAdapter. notifyDataSetChanged ();
Break;
Case FileDownloadHelper. MESSAGE_STOP: // the download is complete.
P = mDownloadAdapter. getItem (url );
FileBusiness. insertFile (getActivity (), p );
Break;
Case FileDownloadHelper. MESSAGE_ERROR:
Toast. makeText (getActivity (), url, Toast. LENGTH_LONG). show ();
Break;
}
Super. handleMessage (msg );
}
};
Code Description: a. mTempListView is added and hidden by default. For more information, see layout.
B. download process: Start (display mTempListView)-> download in progress (Update Progress image and size)-> finish (import pants)
Dialog
If (FileUtils. isVideoOrAudio (url )){
Dialog dialog = new AlertDialog. builder (getActivity ()). setIcon (android. r. drawable. btn_star ). setTitle ("play/download "). setMessage (url ). setPositiveButton ("play", new OnClickListener (){
@ Override
Public void onClick (DialogInterface dialog, int which ){
Intent intent = new Intent (getActivity (), VideoPlayerActivity. class );
Intent. putExtra ("path", url );
StartActivity (intent );
}
}). SetNeutralButton ("Download", new OnClickListener (){
@ Override
Public void onClick (DialogInterface dialog, int which ){
MainFragmentActivity activity = (MainFragmentActivity) getActivity ();
Activity. mFileDownload. newDownloadFile (url );
Toast. makeText (getActivity (), "download..." + FileUtils. getUrlFileName (url) + ", you can view the progress from the local video! ", Toast. LENGTH_LONG). show ();
}
}). SetNegativeButton ("cancel", null). create ();
Dialog. show ();
Return true;
}
Iii. Download
After this chapter, the Code will no longer be downloaded. Please go to Google Code:
Http://code.google.com/p/android-oplayer
Iv. Vitamio announcement
Formally established the Vitamio developer Alliance QQ group! Group Number:246969281
Note:Currently, only developers who have developed Vitamio-based products are allowed to join the application.For the reason, please enter the terms and links of the product to get the latest progress and directly communicate with the author of Vitamio!
EndIt's not terrible to have bugs. Just change it. You can boldly design, write the code, and carefully process known details so that the software will get better and better. After writing the code for one morning, errors are inevitable ~