Python - FFmpeg


before

FFmpeg不屬於Python的包,只是Python在處理音視頻的時候,可能會用到這個工具......

about

引用百度百科,FFmpeg是一套可以用來記錄、轉換數字音頻、視頻,並能將其轉化為流的開源計算機程序。采用LGPL或GPL許可證。它提供了錄制、轉換以及流化音視頻的完整解決方案。它包含了非常先進的音頻/視頻編解碼庫libavcodec,為了保證高可移植性和編解碼質量,libavcodec里很多code都是從頭開發的。

FFmpeg在Linux平台下開發,但它同樣也可以在其它操作系統環境中編譯運行,包括Windows、Mac OS X等。這個項目最早由Fabrice Bellard發起,2004年至2015年間由Michael Niedermayer主要負責維護。許多FFmpeg的開發人員都來自MPlayer項目,而且當前FFmpeg也是放在MPlayer項目組的服務器上。項目的名稱來自MPEG視頻編碼標准,前面的"FF"代表"Fast Forward"。

官網:https://www.ffmpeg.org/
Github地址:https://github.com/FFmpeg/FFmpeg
百度網盤鏈接:https://pan.baidu.com/s/1UBcoXy6v3XG8oz0GuMKd8w 提取碼:90ow

ffmpeg組成

構成FFmpeg主要有三個部分:

第一部分是四個作用不同的工具軟件,分別是:ffmpeg.exe,ffplay.exe,ffserver.exe和ffprobe.exe。

  • ffmpeg.exe:音視頻轉碼、轉換器
  • ffplay.exe:簡單的音視頻播放器
  • ffserver.exe:流媒體服務器
  • ffprobe.exe:簡單的多媒體碼流分析器

第二部分是可以供開發者使用的SDK,為各個不同平台編譯完成的庫。如果說上面的四個工具軟件都是完整成品形式的玩具,那么這些庫就相當於樂高積木一樣,我們可以根據自己的需求使用這些庫開發自己的應用程序。這些庫有:

  • libavcodec:包含音視頻編碼器和解碼器
  • libavutil:包含多媒體應用常用的簡化編程的工具,如隨機數生成器、數據結構、數學函數等功能
  • libavformat:包含多種多媒體容器格式的封裝、解封裝工具
  • libavfilter:包含多媒體處理常用的濾鏡功能
  • libavdevice:用於音視頻數據采集和渲染等功能的設備相關
  • libswscale:用於圖像縮放和色彩空間和像素格式轉換功能
  • libswresample:用於音頻重采樣和格式轉換等功能

第三部分是整個工程的源代碼,無論是編譯出來的可執行程序還是SDK,都是由這些源代碼編譯出來的。FFmpeg的源代碼由C語言實現,主要在Linux平台上進行開發。FFmpeg不是一個孤立的工程,它還存在多個依賴的第三方工程來增強它自身的功能。在當前這一系列的博文/視頻中,我們暫時不會涉及太多源代碼相關的內容,主要以FFmpeg的工具和SDK的調用為主。到下一系列我們將專門研究如何編譯源代碼並根據源代碼來進行二次開發。

FFmpeg for Windows

下載

打開官網下載地址:http://ffmpeg.org/download.html

在下載頁面上,我們可以看到,對於32位和64位版本,分別提供了三種不同的模式:static、shared和dev:

  • static: 該版本提供了靜態版本的FFmpeg工具,將依賴的庫生成在了最終的可執行文件中;作為工具而言此版本就可以滿足我們的需求;
  • share: 該版本的工具包括可執行文件和dll,程序運行過程必須依賴於提供的dll文件;
  • dev: 提供了庫的頭文件和dll的引導庫;

這里我選擇static版本的。

完事點擊下載即可。

安裝

將下載到本地的壓縮包解壓到合適的位置。

比如我將它解壓到G:\software目錄。

配置環境變量

復制軟件的bin目錄路徑G:\software\ffmpeg-4.2.1-win64-static\bin,將它添加到系統環境變量的Path中:

測試

終端執行ffmpeg -version命令查看是否安裝成功:

PS:可能有的電腦重啟才能生效....

OK,安裝成功。

usage

先說我之前遇到的問題,我使用OpenCV(4.1.1.26版本)錄制屏幕,然后保存為MP4視頻,最開始是保存AVI的,誰知道,這兩種在前端video標簽都無法正常播放。

后來,才知道MP4並不是簡單地.mp4就是我們看到的MP4了。有別的視頻編碼格式不對,瀏覽器仍然無法識別。

經過分析,瀏覽器支持的video標簽識別h264編碼的MP4視頻。我才有了查詢我用OpenCV錄制的視頻格式的想法。這不是就用到了FFmpeg這個好用的東東。

查看編碼

ffmpeg -i test.mp4

示例:

C:\Users\Anthony>ffmpeg -i M:\demo\AT2\more\test.mp4
Stream #0:0(und): Video: mpeg4 (Simple Profile) (mp4v / 0x7634706D)

省略了其他部分,重點看Video: mpeg4,沒錯,我用OpenCV錄制的是mpeg4格式的MP4視頻。雖然本地能播放,但瀏覽器卻不能播放,反正我的谷歌和火狐瀏覽器都不能播放,但用別的電腦卻可以,這個結果讓我一度認為我的視頻沒問題......有大神知道怎么回事的,歡迎指正。

在看個我的瀏覽器能播放的:

C:\Users\Anthony>ffmpeg -i M:\demo\AT2\more\b.mp4
Stream #0:0(und): Video: h264 (Constrained Baseline) (avc1 / 

沒錯,h264格式!

不糾結其中的原因,只思考解決辦法,我只要把mpeg4格式的轉換為h264格式的不就完了嘛,是的,我也是這么干的。

視頻編碼轉換

是的,將編碼方式是mpeg4格式的MP4視頻轉換為h264格式的MP4視頻。

mpeg4轉h264

終端執行:

ffmpeg -i input.mp4 -vcodec h264 output.mp4  //input.mp4是指要轉換視頻的地址;output.mp4是轉化后視頻的存放路徑

h264轉mpeg4

ffmpeg -i input.mp4 -vcodec mpeg4 output.mp4

問題

上面的問題,終端使用就沒問題,但是,全部使用Python代碼來解決還是會出現一些問題。

就是在使用Python執行終端命令時,出現問題。

問題1

使用下面命令時會提示,ffmpeg不是可執行的命令,意思是說,Python沒有找到ffmpeg可執行文件,也可能是我下面代碼寫的有問題。

subprocess.Popen('ffmpeg -i {} -vcode h264 {}'.format('./test.mp4', './test1.mp4'), shell=True, stdout=subprocess.PIPE, stderr=subprocess.STDOUT)

解決辦法:

  • 法1,將ffmpeg.exe文件拷貝與腳本文件同級目錄即可。
  • 法2,拿到ffmpeg.exe文件的絕對路徑也一樣。

我選擇法2,但是依然轉碼失敗。

后來,我下載了一個Python相關庫:

pip install ffmpy3
pip install ffmpy3==3-0.2.3

使用ffmp3解決問題:

import ffmpy3
ffmpy3.FFmpeg(inputs={'./test.mp4': None}, outputs={'test1.mp4':None}).run()

關於ffmp3的其他用法,參考:https://ffmpy3.readthedocs.io/en/latest/index.html

當然,此時的ffmpeg.exe可執行文件仍然在腳本的同級目錄,不然依然報錯:

ffmpy3.FFExecutableNotFoundError: Executable 'ffmpeg' not found

完整示例:

import cv2
import numpy as np
from PIL import ImageGrab
from threading import Thread
import ffmpy3

a = False


def f1():
    ffmpy3.FFmpeg(inputs={'./test.mp4': None}, outputs={'test1.mp4': None}).run()


def f2():
    p = ImageGrab.grab()
    width, height = p.size
    fourcc = cv2.VideoWriter_fourcc('m', 'p', '4', 'v')

    video = cv2.VideoWriter('./test.mp4', fourcc, 8, (width, height), True)
    while 1:
        img = ImageGrab.grab()
        img_bgr = cv2.cvtColor(np.array(img), cv2.COLOR_RGB2BGR)
        video.write(img_bgr)
        if a:
            break
    video.release()
    f1()

def f3():
    global a
    import time
    time.sleep(3)
    a = True


if __name__ == '__main__':
    Thread(target=f3).start()
    f2()

歡迎斧正,that's all see also:[mp4格式的視頻,編碼方式mpeg4,轉化為h264](https://www.cnblogs.com/shuaifing/p/9593808.html) | [Ffmpeg常用轉碼命令](https://www.cnblogs.com/yuancr/p/7272321.html) | [FFmpeg安裝(windows環境)]( ) | [Python-OpenCV錄制H264編碼的MP4視頻]( ) | [H264 encoding failure]( ) | [video不能播放mp4的問題(一)]( ) | [HTML video 標簽]( ) | [FFmpeg Builds]( ) | [ffmpy3](https://ffmpy3.readthedocs.io/en/latest/index.html) | [python ffmpy3與FFmpeg的安裝](https://blog.csdn.net/qq_40962368/article/details/90748852) | [python 使用 ffmpeg](https://blog.csdn.net/qq_34971175/article/details/79485665) | []()


免責聲明!

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



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