视频转码
一、視頻轉碼
import java.io.File; import java.io.IOException; import java.io.InputStream; import java.util.Date; import java.util.List;import com.wdy.common.Contants;public class ConverVideoUtils {private Date dt;private long begintime;private String sourceVideoPath;//源視頻路徑private String filerealname; // 文件名 不包括擴展名private String filename; // 包括擴展名private String videofolder = Contants.videofolder; // 別的格式視頻的目錄private String targetfolder = Contants.targetfolder; // flv視頻的目錄private String ffmpegpath = Contants.ffmpegpath; // ffmpeg.exe的目錄private String mencoderpath = Contants.mencoderpath; // mencoder的目錄private String imageRealPath = Contants.imageRealPath; // 截圖的存放目錄public ConverVideoUtils() {}public ConverVideoUtils(String path) {sourceVideoPath = path;}public String getPATH() {return sourceVideoPath;}public void setPATH(String path) {sourceVideoPath = path;}/*** 轉換視頻格式* @param String targetExtension 目標視頻擴展名 .xxx * @param isDelSourseFile 轉換完成后是否刪除源文件* @return*/public boolean beginConver(String targetExtension, boolean isDelSourseFile) {File fi = new File(sourceVideoPath);filename = fi.getName();filerealname = filename.substring(0, filename.lastIndexOf(".")).toLowerCase();System.out.println("----接收到文件(" + sourceVideoPath + ")需要轉換-------------------------- ");if (!checkfile(sourceVideoPath)) {System.out.println(sourceVideoPath + "文件不存在" + " ");return false;}dt = new Date();begintime = dt.getTime();System.out.println("----開始轉文件(" + sourceVideoPath + ")-------------------------- ");if (process(targetExtension,isDelSourseFile)) {Date dt2 = new Date();System.out.println("轉換成功 ");long endtime = dt2.getTime();long timecha = (endtime - begintime);String totaltime = sumTime(timecha);System.out.println("轉換視頻格式共用了:" + totaltime + " ");if (processImg(sourceVideoPath)) {System.out.println("截圖成功了! ");} else {System.out.println("截圖失敗了! ");}if (isDelSourseFile) {deleteFile(sourceVideoPath);}sourceVideoPath = null;return true;} else {sourceVideoPath = null;return false;}}/*** 對視頻進行截圖* @param sourceVideoPath 需要被截圖的視頻路徑(包含文件名和擴展名)* @return*/public boolean processImg(String sourceVideoPath) {if (!checkfile(sourceVideoPath)) {System.out.println(sourceVideoPath + " is not file");return false;}File fi = new File(sourceVideoPath);filename = fi.getName();filerealname = filename.substring(0, filename.lastIndexOf(".")).toLowerCase();List<String> commend = new java.util.ArrayList<String>();//第一幀: 00:00:01//time ffmpeg -ss 00:00:01 -i test1.flv -f image2 -y test1.jpgcommend.add(ffmpegpath); // commend.add("-i"); // commend.add(videoRealPath + filerealname + ".flv"); // commend.add("-y"); // commend.add("-f"); // commend.add("image2"); // commend.add("-ss"); // commend.add("38"); // commend.add("-t"); // commend.add("0.001"); // commend.add("-s"); // commend.add("320x240");commend.add("-ss");commend.add("00:00:01");commend.add("-i");commend.add(sourceVideoPath);commend.add("-f");commend.add("image2");commend.add("-y");commend.add(imageRealPath + filerealname + ".jpg");try {ProcessBuilder builder = new ProcessBuilder();builder.command(commend);builder.start();return true;} catch (Exception e) {e.printStackTrace();return false;}}/*** 實際轉換視頻格式的方法* @param targetExtension 目標視頻擴展名* @param isDelSourseFile 轉換完成后是否刪除源文件* @return*/private boolean process(String targetExtension, boolean isDelSourseFile) {int type = checkContentType();boolean status = false;if (type == 0) {//如果type為0用ffmpeg直接轉換status = processVideoFormat(sourceVideoPath,targetExtension, isDelSourseFile);} else if (type == 1) {//如果type為1,將其他文件先轉換為avi,然后在用ffmpeg轉換為指定格式String avifilepath = processAVI(type);if (avifilepath == null){// avi文件沒有得到return false;}else {System.out.println("開始轉換:");status = processVideoFormat(avifilepath,targetExtension, isDelSourseFile);}}return status;}/*** 檢查文件類型* @return*/private int checkContentType() {String type = sourceVideoPath.substring(sourceVideoPath.lastIndexOf(".") + 1, sourceVideoPath.length()).toLowerCase();// ffmpeg能解析的格式:(asx,asf,mpg,wmv,3gp,mp4,mov,avi,flv等)if (type.equals("avi")) {return 0;} else if (type.equals("mpg")) {return 0;} else if (type.equals("wmv")) {return 0;} else if (type.equals("3gp")) {return 0;} else if (type.equals("mov")) {return 0;} else if (type.equals("mp4")) {return 0;} else if (type.equals("asf")) {return 0;} else if (type.equals("asx")) {return 0;} else if (type.equals("flv")) {return 0;}// 對ffmpeg無法解析的文件格式(wmv9,rm,rmvb等),// 可以先用別的工具(mencoder)轉換為avi(ffmpeg能解析的)格式.else if (type.equals("wmv9")) {return 1;} else if (type.equals("rm")) {return 1;} else if (type.equals("rmvb")) {return 1;}return 9;}/*** 檢查文件是否存在* @param path* @return*/private boolean checkfile(String path) {File file = new File(path);if (!file.isFile()) {return false;} else {return true;}}/*** 對ffmpeg無法解析的文件格式(wmv9,rm,rmvb等), 可以先用別的工具(mencoder)轉換為avi(ffmpeg能解析的)格式.* @param type* @return*/private String processAVI(int type) {List<String> commend = new java.util.ArrayList<String>();commend.add(mencoderpath);commend.add(sourceVideoPath);commend.add("-oac");commend.add("mp3lame");commend.add("-lameopts");commend.add("preset=64");commend.add("-ovc");commend.add("xvid");commend.add("-xvidencopts");commend.add("bitrate=600");commend.add("-of");commend.add("avi");commend.add("-o");commend.add(videofolder + filerealname + ".avi");// 命令類型:mencoder 1.rmvb -oac mp3lame -lameopts preset=64 -ovc xvid// -xvidencopts bitrate=600 -of avi -o rmvb.avitry {ProcessBuilder builder = new ProcessBuilder();builder.command(commend);Process p = builder.start();doWaitFor(p);return videofolder + filerealname + ".avi";} catch (Exception e) {e.printStackTrace();return null;}}/*** 轉換為指定格式* ffmpeg能解析的格式:(asx,asf,mpg,wmv,3gp,mp4,mov,avi,flv等)* @param oldfilepath* @param targetExtension 目標格式擴展名 .xxx* @param isDelSourseFile 轉換完成后是否刪除源文件* @return*/private boolean processVideoFormat(String oldfilepath, String targetExtension, boolean isDelSourceFile) {if (!checkfile(sourceVideoPath)) {System.out.println(oldfilepath + " is not file");return false;}//ffmpeg -i FILE_NAME.flv -ar 22050 NEW_FILE_NAME.mp4List<String> commend = new java.util.ArrayList<>();commend.add(ffmpegpath);commend.add("-i");commend.add(oldfilepath);commend.add("-ar");commend.add("22050");commend.add(targetfolder + filerealname + targetExtension);try {ProcessBuilder builder = new ProcessBuilder();String cmd = commend.toString();builder.command(commend);Process p = builder.start();doWaitFor(p);p.destroy();//轉換完成后刪除源文件 // if (isDelSourceFile) { // deleteFile(sourceVideoPath); // }return true;} catch (Exception e) {e.printStackTrace();return false;}}/*** ffmpeg能解析的格式:(asx,asf,mpg,wmv,3gp,mp4,mov,avi,flv等)* @param oldfilepath* @return*/private boolean processFLV(String oldfilepath) {if (!checkfile(sourceVideoPath)) {System.out.println(oldfilepath + " is not file");return false;}List<String> commend = new java.util.ArrayList<>();commend.add(ffmpegpath);commend.add("-i");commend.add(oldfilepath);commend.add("-ab");commend.add("64");commend.add("-acodec");commend.add("mp3");commend.add("-ac");commend.add("2");commend.add("-ar");commend.add("22050");commend.add("-b");commend.add("230");commend.add("-r");commend.add("24");commend.add("-y");commend.add(targetfolder + filerealname + ".flv");try {ProcessBuilder builder = new ProcessBuilder();String cmd = commend.toString();builder.command(commend);Process p = builder.start();doWaitFor(p);p.destroy();deleteFile(oldfilepath);return true;} catch (Exception e) {e.printStackTrace();return false;}}public int doWaitFor(Process p) {InputStream in = null;InputStream err = null;int exitValue = -1; // returned to caller when p is finishedtry {System.out.println("comeing");in = p.getInputStream();err = p.getErrorStream();boolean finished = false; // Set to true when p is finishedwhile (!finished) {try {while (in.available() > 0) {Character c = new Character((char) in.read());System.out.print(c);}while (err.available() > 0) {Character c = new Character((char) err.read());System.out.print(c);}exitValue = p.exitValue();finished = true;} catch (IllegalThreadStateException e) {Thread.currentThread().sleep(500);}}} catch (Exception e) {System.err.println("doWaitFor();: unexpected exception - " + e.getMessage());} finally {try {if (in != null) {in.close();}} catch (IOException e) {System.out.println(e.getMessage());}if (err != null) {try {err.close();} catch (IOException e) {System.out.println(e.getMessage());}}}return exitValue;}/**二、測試的案例
package com.royLuo.main.converter.ffmpeg;import java.io.IOException; import java.io.InputStream; import java.io.InputStreamReader; import java.util.ArrayList; import java.util.List;public class Demo01 {public static void main(String[] args) { // test(); // test2(); // test3(); // test4();test5(); // test6();}public static void test() {ProcessBuilder processBuilder = new ProcessBuilder();//定義命令內容List<String> command = new ArrayList<String>();command.add("D:\\luojunrong-gitee\\videoManage\\ffmpeg\\bin\\ffmpeg.exe");command.add("-i");//被轉碼的視頻command.add("D:\\測試視頻\\20d008203b85e2ff85ba20f4c54b474f.mp4");command.add("-y");//覆蓋輸出文件command.add("-c:v");command.add("libx264");//設定畫面的寬高command.add("-s");command.add("1280x720");command.add("-pix_fmt");command.add("yuv420p");//音頻碼率command.add("-b:a");command.add("63k");//視頻碼率command.add("-b:v");command.add("753k");command.add("-r");command.add("18");command.add("D:\\luojunrong-gitee\\videoManage\\test-fmpeg\\1.rmvb");processBuilder.command(command);//將標準輸入流和錯誤輸入流合并,通過標準輸入流讀取信息processBuilder.redirectErrorStream(true);try {//啟動進程Process start = processBuilder.start();//獲取輸入流InputStream inputStream = start.getInputStream();//轉成字符輸入流InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "gbk");int len = -1;char[] c = new char[1024];StringBuffer outputString = new StringBuffer();//讀取進程輸入流中的內容while ((len = inputStreamReader.read(c)) != -1) {String s = new String(c, 0, len);outputString.append(s);System.out.print(s);}inputStream.close();} catch (Exception e) {e.printStackTrace();}}/*** 截取一張352x240尺寸大小的,格式為jpg的圖片* ffmpeg -i test.asf -y -f image2 -t 0.001 -s 352x240 a.jpg**/public static void test2() {ProcessBuilder processBuilder = new ProcessBuilder();//定義命令內容// ffmpeg -i test.asf -y -f image2 -t 0.001 -s 352x240 a.jpgList<String> command = new ArrayList<String>();command.add("D:\\luojunrong-gitee\\videoManage\\ffmpeg\\bin\\ffmpeg.exe");command.add("-i");//被轉碼的視頻command.add("D:\\測試視頻\\20d008203b85e2ff85ba20f4c54b474f.mp4");command.add("-y");//覆蓋輸出文件command.add("-f");command.add("image2");command.add("-t");command.add("0.001");//-s 設置分辨率 // command.add("-s"); // command.add("1280x720");command.add("D:\\luojunrong-gitee\\videoManage\\test-fmpeg\\20d008203b85e2ff85ba20f4c54b474f.jpg");processBuilder.command(command);//將標準輸入流和錯誤輸入流合并,通過標準輸入流讀取信息processBuilder.redirectErrorStream(true);try {//啟動進程Process start = processBuilder.start();//獲取輸入流InputStream inputStream = start.getInputStream();//轉成字符輸入流InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "gbk");int len = -1;char[] c = new char[1024];StringBuffer outputString = new StringBuffer();//讀取進程輸入流中的內容while ((len = inputStreamReader.read(c)) != -1) {String s = new String(c, 0, len);outputString.append(s);System.out.print(s);}inputStream.close();} catch (Exception e) {e.printStackTrace();}}/**** 1秒24幀* 把視頻的前30幀轉換成一個 gif* ffmpeg -i test.asf -vframes 30 -y -f gif a.gif* */public static void test3() {ProcessBuilder processBuilder = new ProcessBuilder();//定義命令內容// ffmpeg -i test.asf -vframes 30 -y -f gif a.gifList<String> command = new ArrayList<String>();command.add("D:\\luojunrong-gitee\\videoManage\\ffmpeg\\bin\\ffmpeg.exe");command.add("-i");//被轉碼的視頻command.add("D:\\測試視頻\\20d008203b85e2ff85ba20f4c54b474f.mp4");command.add("-vframes");command.add("72");command.add("-y");command.add("-f");command.add("gif");// 1280x720 高清// 1920×1080 超清 // command.add("-s"); // command.add("1280x720");command.add("D:\\luojunrong-gitee\\videoManage\\test-fmpeg\\20d008203b85e2ff85ba20f4c54b474f.gif");processBuilder.command(command);//將標準輸入流和錯誤輸入流合并,通過標準輸入流讀取信息processBuilder.redirectErrorStream(true);try {//啟動進程Process start = processBuilder.start();//獲取輸入流InputStream inputStream = start.getInputStream();//轉成字符輸入流InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "gbk");int len = -1;char[] c = new char[1024];StringBuffer outputString = new StringBuffer();//讀取進程輸入流中的內容while ((len = inputStreamReader.read(c)) != -1) {String s = new String(c, 0, len);outputString.append(s);System.out.print(s);}inputStream.close();} catch (Exception e) {e.printStackTrace();}}/*** ffmpeg -i 1.mp4 -codec copy -vbsf h264_mp4toannexb 1.ts**///todopublic static void test4() {ProcessBuilder processBuilder = new ProcessBuilder();//定義命令內容// ffmpeg -i test.asf -vframes 30 -y -f gif a.gifList<String> command = new ArrayList<String>();command.add("D:\\luojunrong-gitee\\videoManage\\ffmpeg\\bin\\ffmpeg.exe");command.add("-i");//被轉碼的視頻command.add("D:\\luojunrong-gitee\\videoManage\\test-fmpeg\\20d008203b85e2ff85ba20f4c54b474f.3gp");command.add("-codec");command.add("copy");command.add("-vbsf");command.add("h264_mp4toannexb");command.add("-y");//wmv,3gp,mp4,mov,avi,flv,ts,mkvcommand.add("D:\\luojunrong-gitee\\videoManage\\test-fmpeg\\mp4\\20d008203b85e2ff85ba20f4c54b474f.mp4");processBuilder.command(command);//將標準輸入流和錯誤輸入流合并,通過標準輸入流讀取信息processBuilder.redirectErrorStream(true);try {//啟動進程Process start = processBuilder.start();//獲取輸入流InputStream inputStream = start.getInputStream();//轉成字符輸入流InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "gbk");int len = -1;char[] c = new char[1024];StringBuffer outputString = new StringBuffer();//讀取進程輸入流中的內容while ((len = inputStreamReader.read(c)) != -1) {String s = new String(c, 0, len);outputString.append(s);System.out.print(s);}inputStream.close();} catch (Exception e) {e.printStackTrace();}}public static void test5() {ProcessBuilder processBuilder = new ProcessBuilder();//定義命令內容// ffmpeg -i test.asf -vframes 30 -y -f gif a.gifList<String> command = new ArrayList<String>();command.add("D:\\luojunrong-gitee\\videoManage\\ffmpeg\\bin\\ffmpeg.exe");command.add("-i");//被轉碼的視頻command.add("D:\\測試視頻\\音樂之聲-njluyou.rm");command.add("-vcodec");command.add("wmv1");command.add("D:\\luojunrong-gitee\\videoManage\\test-fmpeg\\20d008203b85e2ff85ba20f4c54b474f.mp4");processBuilder.command(command);//將標準輸入流和錯誤輸入流合并,通過標準輸入流讀取信息processBuilder.redirectErrorStream(true);try {//啟動進程Process start = processBuilder.start();//獲取輸入流InputStream inputStream = start.getInputStream();//轉成字符輸入流InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "gbk");int len = -1;char[] c = new char[1024];StringBuffer outputString = new StringBuffer();//讀取進程輸入流中的內容while ((len = inputStreamReader.read(c)) != -1) {String s = new String(c, 0, len);outputString.append(s);System.out.print(s);}inputStream.close();} catch (Exception e) {e.printStackTrace();}}/*** -oac mp3lame -lameopts preset=64 -ovc xvid -xvidencopts** bitrate=600 -of avi -o** **/// 對ffmpeg無法解析的文件格式(wmv9,rm,rmvb等), 可以先用別的工具(mencoder)轉換為avi(ffmpeg能解析的)格式.public static void test6() {ProcessBuilder processBuilder = new ProcessBuilder();//定義命令內容// ffmpeg -i test.asf -vframes 30 -y -f gif a.gifList<String> command = new ArrayList<String>();command.add("D:\\luojunrong-gitee\\videoManage\\MPlayer-mingw32-1.0rc1\\mplayer\\mencoder");command.add("D:\\測試視頻\\音樂之聲-njluyou.rm");command.add("-oac");command.add("mp3lame");command.add("-lameopts");command.add("preset=64");command.add("-ovc");command.add("xvid");command.add("-xvidencopts");command.add("bitrate=600");command.add("-of");command.add("avi");command.add("-o");command.add("D:\\luojunrong-gitee\\videoManage\\test-fmpeg\\音樂之聲-njluyou.avi");processBuilder.command(command);//將標準輸入流和錯誤輸入流合并,通過標準輸入流讀取信息processBuilder.redirectErrorStream(true);try {//啟動進程Process start = processBuilder.start();//獲取輸入流InputStream inputStream = start.getInputStream();//轉成字符輸入流InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "gbk");int len = -1;char[] c = new char[1024];StringBuffer outputString = new StringBuffer();//讀取進程輸入流中的內容while ((len = inputStreamReader.read(c)) != -1) {String s = new String(c, 0, len);outputString.append(s);System.out.print(s);}inputStream.close();} catch (Exception e) {e.printStackTrace();}}}通用選項
-L license-h 幫助-fromats 顯示可用的格式,編解碼的,協議的。。。-f fmt 強迫采用格式fmt-I filename 輸入文件-y 覆蓋輸出文件-t duration 設置紀錄時間 hh:mm:ss[.xxx]格式的記錄時間也支持-ss position 搜索到指定的時間 [-]hh:mm:ss[.xxx]的格式也支持-title string 設置標題-author string 設置作者-copyright string 設置版權-comment string 設置評論-target type 設置目標文件類型(vcd,svcd,dvd) 所有的格式選項(比特率,編解碼以及緩沖區大小)自動設置 ,只需要輸入如下的就可以了: ffmpeg -i myfile.avi -target vcd /tmp/vcd.mpg-hq 激活高質量設置-itsoffset offset 設置以秒為基準的時間偏移,該選項影響所有后面的輸入文件。該偏移被加到輸入文件的時戳,定義一個正偏移意味著相應的流被延遲了 offset秒。 [-]hh:mm:ss[.xxx]的格式也支持視頻選項
-b bitrate 設置比特率,缺省200kb/s-r fps 設置幀頻 缺省25-s size 設置幀大小 格式為WXH 缺省160X128.下面的簡寫也可以直接使用: Sqcif 128X96 qcif 176X144 cif 252X288 4cif 704X576-aspect aspect 設置橫縱比 4:3 16:9 或 1.3333 1.7777-croptop size 設置頂部切除帶大小 像素單位-cropbottom size –cropleft size –cropright size-padtop size 設置頂部補齊的大小 像素單位-padbottom size –padleft size –padright size –padcolor color 設置補齊條顏色(hex,6個16進制的數,紅:綠:蘭排列,比如 000000代表黑色)-vn 不做視頻記錄-bt tolerance 設置視頻碼率容忍度kbit/s-maxrate bitrate設置最大視頻碼率容忍度-minrate bitreate 設置最小視頻碼率容忍度-bufsize size 設置碼率控制緩沖區大小-vcodec codec 強制使用codec編解碼方式。 如果用copy表示原始編解碼數據必須被拷貝。-sameq 使用同樣視頻質量作為源(VBR)-pass n 選擇處理遍數(1或者2)。兩遍編碼非常有用。第一遍生成統計信息,第二遍生成精確的請求的碼率-passlogfile file 選擇兩遍的紀錄文件名為file高級選項
-g gop_size 設置圖像組大小-intra 僅適用幀內編碼-qscale q 使用固定的視頻量化標度(VBR)-qmin q 最小視頻量化標度(VBR)-qmax q 最大視頻量化標度(VBR)-qdiff q 量化標度間最大偏差 (VBR)-qblur blur 視頻量化標度柔化(VBR)-qcomp compression 視頻量化標度壓縮(VBR)-rc_init_cplx complexity 一遍編碼的初始復雜度-b_qfactor factor 在p和b幀間的qp因子-i_qfactor factor 在p和i幀間的qp因子-b_qoffset offset 在p和b幀間的qp偏差-i_qoffset offset 在p和i幀間的qp偏差-rc_eq equation 設置碼率控制方程 默認tex^qComp-rc_override override 特定間隔下的速率控制重載-me method 設置運動估計的方法 可用方法有 zero phods log x1 epzs(缺省) full-dct_algo algo 設置dct的算法 可用的有 0 FF_DCT_AUTO 缺省的DCT 1 FF_DCT_FASTINT 2 FF_DCT_INT 3 FF_DCT_MMX 4 FF_DCT_MLIB 5 FF_DCT_ALTIVEC-idct_algo algo 設置idct算法。可用的有 0 FF_IDCT_AUTO 缺省的IDCT 1 FF_IDCT_INT 2 FF_IDCT_SIMPLE 3 FF_IDCT_SIMPLEMMX 4 FF_IDCT_LIBMPEG2MMX 5 FF_IDCT_PS2 6 FF_IDCT_MLIB 7 FF_IDCT_ARM 8 FF_IDCT_ALTIVEC 9 FF_IDCT_SH4 10 FF_IDCT_SIMPLEARM-er n 設置錯誤殘留為n 1 FF_ER_CAREFULL 缺省 2 FF_ER_COMPLIANT 3 FF_ER_AGGRESSIVE 4 FF_ER_VERY_AGGRESSIVE-ec bit_mask 設置錯誤掩蔽為bit_mask,該值為如下值的位掩碼 1 FF_EC_GUESS_MVS (default=enabled) 2 FF_EC_DEBLOCK (default=enabled)-bf frames 使用frames B 幀,支持mpeg1,mpeg2,mpeg4-mbd mode 宏塊決策 0 FF_MB_DECISION_SIMPLE 使用mb_cmp 1 FF_MB_DECISION_BITS 2 FF_MB_DECISION_RD-4mv 使用4個運動矢量 僅用于mpeg4-part 使用數據劃分 僅用于mpeg4-bug param 繞過沒有被自動監測到編碼器的問題-strict strictness 跟標準的嚴格性-aic 使能高級幀內編碼 h263+-umv 使能無限運動矢量 h263+-deinterlace 不采用交織方法-interlace 強迫交織法編碼 僅對mpeg2和mpeg4有效。當你的輸入是交織的并且你想要保持交織以最小圖像損失的時候采用該選項。可選的方法是不交織,但是損失更大-psnr 計算壓縮幀的psnr-vstats 輸出視頻編碼統計到vstats_hhmmss.log-vhook module 插入視頻處理模塊 module 包括了模塊名和參數,用空格分開音頻選項
-ab bitrate 設置音頻碼率-ar freq 設置音頻采樣率-ac channels 設置通道 缺省為1-an 不使能音頻紀錄-acodec codec 使用codec編解碼音視頻捕獲選項
-vd device 設置視頻捕獲設備。比如/dev/video0-vc channel 設置視頻捕獲通道 DV1394專用-tvstd standard 設置電視標準 NTSC PAL(SECAM)-dv1394 設置DV1394捕獲-av device 設置音頻設備 比如/dev/dsp高級選項
-map file:stream 設置輸入流映射-debug 打印特定調試信息-benchmark 為基準測試加入時間-hex 傾倒每一個輸入包-bitexact 僅使用位精確算法 用于編解碼測試-ps size 設置包大小,以bits為單位-re 以本地幀頻讀數據,主要用于模擬捕獲設備-loop 循環輸入流。只工作于圖像流,用于ffserver測試參考文章:https://blog.csdn.net/wdy_2099/article/details/71453602
總結
- 上一篇: 汽车维修企业管理【2】
- 下一篇: leetcode + 腾讯面试