[轉]android 獲取視頻幀


本文轉自:http://blog.csdn.net/heart_Moving/article/details/17414067

今天做Android視頻文件解碼,需求:從一個視頻文件獲取到一幀一幀的圖片。

總結如下:

首先看代碼:

MediaDecoder.java

  1. import android.graphics.Bitmap;  
  2. import android.media.MediaMetadataRetriever;  
  3. import android.util.Log;  
  4.   
  5. public class MediaDecoder {  
  6.     private static final String TAG = "MediaDecoder";  
  7.     private MediaMetadataRetriever retriever = null;  
  8.     private String fileLength;  
  9.   
  10.     public MediaDecoder(String file) {  
  11.         if(CommonUtils.checkFile(file)){  
  12.             retriever = new MediaMetadataRetriever();  
  13.             retriever.setDataSource(file);  
  14.             fileLength = retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_DURATION);  
  15.             Log.i(TAG, "fileLength : "+fileLength);  
  16.         }  
  17.     }  
  18.     /**  
  19.      * 獲取視頻某一幀  
  20.      * @param timeMs 毫秒  
  21.      * @param listener   
  22.      */  
  23.     public boolean decodeFrame(long timeMs,OnGetBitmapListener listener){  
  24.         if(retriever == null) return false;  
  25.         Bitmap bitmap = retriever.getFrameAtTime(timeMs * 1000, MediaMetadataRetriever.OPTION_CLOSEST);  
  26.         if(bitmap == null) return false;  
  27.         listener.getBitmap(bitmap, timeMs);   
  28.         return true;  
  29.     }  
  30.     /**  
  31.      * 取得視頻文件播放長度  
  32.      * @return  
  33.      */  
  34.     public String getVedioFileLength(){  
  35.         return fileLength;  
  36.     }  
  37.   
  38. }  
import android.graphics.Bitmap;
import android.media.MediaMetadataRetriever;
import android.util.Log;

public class MediaDecoder {
	private static final String TAG = "MediaDecoder";
	private MediaMetadataRetriever retriever = null;
	private String fileLength;

	public MediaDecoder(String file) {
		if(CommonUtils.checkFile(file)){
			retriever = new MediaMetadataRetriever();
			retriever.setDataSource(file);
			fileLength = retriever.extractMetadata(MediaMetadataRetriever.METADATA_KEY_DURATION);
			Log.i(TAG, "fileLength : "+fileLength);
		}
	}
	/**
	 * 獲取視頻某一幀
	 * @param timeMs 毫秒
	 * @param listener 
	 */
	public boolean decodeFrame(long timeMs,OnGetBitmapListener listener){
		if(retriever == null) return false;
		Bitmap bitmap = retriever.getFrameAtTime(timeMs * 1000, MediaMetadataRetriever.OPTION_CLOSEST);
		if(bitmap == null) return false;
		listener.getBitmap(bitmap, timeMs);	
		return true;
	}
	/**
	 * 取得視頻文件播放長度
	 * @return
	 */
	public String getVedioFileLength(){
		return fileLength;
	}

}

這里是獲取視頻幀工具,調試的時候遇到一些問題:

 

其中一個是getFrameAtTime參數的使用,先看方法原型:public Bitmap getFrameAtTime(long timeUs, int option) 第一個參數是傳入時間,只能是us(微秒) ,當時我傳入的ms,獲取的總是第一幀,所以這個問題都弄了好久。

然后是第二個參數,先看看官方解釋:

OPTION_CLOSEST    在給定的時間,檢索最近一個幀,這個幀不一定是關鍵幀

OPTION_CLOSEST_SYNC    在給定的時間,檢索最近一個同步與數據源相關聯的的幀(關鍵幀)。

OPTION_NEXT_SYNC  在給定時間之后檢索一個同步與數據源相關聯的關鍵幀。

OPTION_PREVIOUS_SYNC   顧名思義,同上

這里為了提取我們想要的幀,不使用關鍵幀,所以用 OPTION_CLOSEST .

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM