Python调用ffmpeg开源视频处理库,批量处理视频


Posted in Python onNovember 16, 2020

代码示例

# coding=utf-8
import os
import subprocess
import datetime
import json, pprint
import re, time
import threading
import random
import shutil


class FFmpeg:

  def __init__(self, editvdo, addlogo=None, addmusic=None,
         addvdohead=None, addvdotail=None):
    self.editvdo = editvdo
    self.addlogo = addlogo
    self.addmusic = addmusic
    self.addvdohead = addvdohead
    self.addvdotail = addvdotail
    self.vdo_time, self.vdo_width, self.vdo_height, self.attr_dict = self.get_attr()
    self.editvdo_path = os.path.dirname(editvdo)
    self.editvdo_name = os.path.basename(editvdo)

  def get_attr(self):
    """
    获取视频属性参数
    :return:
    """
    strcmd = r'ffprobe -print_format json -show_streams -i "{}"'.format(self.editvdo)
    status, output = subprocess.getstatusoutput(strcmd)
    agrs = eval(re.search('{.*}', output, re.S).group().replace("\n", "").replace(" ", ''))
    streams = agrs.get('streams', [])
    agrs_dict = dict()
    [agrs_dict.update(x) for x in streams]
    vdo_time = agrs_dict.get('duration')
    vdo_width = agrs_dict.get('width')
    vdo_height = agrs_dict.get('height')
    attr = (vdo_time, vdo_width, vdo_height, agrs_dict)
    return attr

  def edit_head(self, start_time, end_time, deposit=None):
    """
    截取指定长度视频
    :param second: 去除开始的多少秒
    :param deposit: 另存为文件
    :return: True/Flase
    """
    if None == deposit:
      deposit = self.editvdo_path+'/'+'edit_head'+self.editvdo_name
    start = time.strftime('%H:%M:%S', time.gmtime(start_time))
    end = time.strftime('%H:%M:%S', time.gmtime(end_time))
    strcmd = 'ffmpeg -i "{}" -vcodec copy -acodec copy -ss {} -to {} "{}" -y'.format(
      self.editvdo, start, end, deposit)
    result = subprocess.run(args=strcmd, stdout=subprocess.PIPE, shell=True)
    if os.path.exists(deposit):
      os.remove(self.editvdo)
      os.rename(deposit, self.editvdo)
      return True
    else:
      return False

  def edit_logo(self, deposit=None):
    """
    添加水印
    :param deposit:添加水印后另存为路径,为空则覆盖
    :return: True/False
    """
    if None == deposit:
      deposit = self.editvdo_path+'/'+'edit_logo'+self.editvdo_name
    strcmd = r'ffmpeg -i "{}" -vf "movie=\'{}\' [watermark];[in] ' \
         r'[watermark] overlay=main_w-overlay_w-10:10 [out]" "{}"'.format(
          self.editvdo, self.addlogo, deposit)
    result = subprocess.run(args=strcmd, stdout=subprocess.PIPE, shell=True)
    if os.path.exists(deposit):
      os.remove(self.editvdo)
      os.rename(deposit, self.editvdo)
      return True
    else:
      return False

  def edit_music(self, deposit=None):
    if None == deposit:
      deposit = self.editvdo_path+'/'+'edit_music'+self.editvdo_name
    strcmd = r'ffmpeg -y -i "{}" -i "{}" -filter_complex "[0:a] ' \
         r'pan=stereo|c0=1*c0|c1=1*c1 [a1], [1:a] ' \
         r'pan=stereo|c0=1*c0|c1=1*c1 [a2],[a1][a2]amix=duration=first,' \
         r'pan=stereo|c0<c0+c1|c1<c2+c3,pan=mono|c0=c0+c1[a]" ' \
         r'-map "[a]" -map 0:v -c:v libx264 -c:a aac ' \
         r'-strict -2 -ac 2 "{}"'.format(self.editvdo, self.addmusic, deposit)
    result = subprocess.run(args=strcmd, stdout=subprocess.PIPE, shell=True)
    if os.path.exists(deposit):
      os.remove(self.editvdo)
      os.rename(deposit, self.editvdo)
      return True
    else:
      return False

  def edit_rate(self, rete=30, deposit=None):
    """
    改变帧率
    :param rete: 修改大小帧率
    :param deposit: 修改后保存路径
    :return:
    """
    if None == deposit:
      deposit = self.editvdo_path+'/'+'edit_music'+self.editvdo_name
    strcmd = r'ffmpeg -i "{}" -r {} "{}"' % (self.editvdo, rete, deposit)
    result = subprocess.run(args=strcmd, stdout=subprocess.PIPE, shell=True)
    if os.path.exists(deposit):
      os.remove(self.editvdo)
      os.rename(deposit, self.editvdo)
      return True
    else:
      return False

  def edit_power(self, power='1280x720', deposit=None):
    """
    修改分辨率
    :param power: 分辨率
    :param deposit: 修改后保存路径,为空则覆盖
    :return:
    """
    if None == deposit:
      deposit = self.editvdo_path+'/'+'edit_power'+self.editvdo_name
    strcmd = r'ffmpeg -i "{}" -s {} "{}"'.format(self.editvdo, power, deposit)
    result = subprocess.run(args=strcmd, stdout=subprocess.PIPE, shell=True)
    if os.path.exists(deposit):
      os.remove(self.editvdo)
      os.rename(deposit, self.editvdo)
      return True
    else:
      return False

  def rdit_marge(self, vdo_head, vdo_tail, deposit=None):
    if None == deposit:
      deposit = self.editvdo_path+'/'+'rdit_marge'+self.editvdo_name
    with open(self.editvdo_path+'/'+'rdit_marge.txt', 'w', encoding='utf-8') as f:
      f.write("file '{}' \nfile '{}' \nfile '{}'" .format(
        vdo_head, self.editvdo, vdo_tail))
    strcmd = r'ffmpeg -f concat -safe 0 -i "{}" -c copy "{}"'.format(
      self.editvdo_path + '/' + 'rdit_marge.txt', deposit)
    result = subprocess.run(args=strcmd, stdout=subprocess.PIPE, shell=True)
    if os.path.exists(deposit):
      os.remove(self.editvdo)
      os.rename(deposit, self.editvdo)
      return True
    else:
      return False



  # ffmpeg - i input.mkv - filter_complex "[0:v]setpts=0.5*PTS[v];[0:a]atempo=2.0[a]" - map"[v]" - map"[a]" output.mkv



test = FFmpeg(r"D:\vdio\4.mp4")
pass

以上就是Python调用ffmpeg开源视频处理库,批量处理视频的详细内容,更多关于python 批量处理视频的资料请关注三水点靠木其它相关文章!

Python 相关文章推荐
Python基于pygame实现图片代替鼠标移动效果
Nov 11 Python
基于python的Tkinter实现一个简易计算器
Dec 31 Python
Python实现的简单dns查询功能示例
May 24 Python
Python实现在线暴力破解邮箱账号密码功能示例【测试可用】
Sep 06 Python
python定时复制远程文件夹中所有文件
Apr 30 Python
tensorflow 获取所有variable或tensor的name示例
Jan 04 Python
django 链接多个数据库 并使用原生sql实现
Mar 28 Python
Python接口测试环境搭建过程详解
Jun 29 Python
如何利用python进行时间序列分析
Aug 04 Python
python 偷懒技巧——使用 keyboard 录制键盘事件
Sep 21 Python
如何将Pycharm中调整字体大小的方式设置为&quot;ctrl+鼠标滚轮上下滑&quot;
Nov 17 Python
Django+Nginx+uWSGI 定时任务的实现方法
Jan 22 Python
python tkinter实现连连看游戏
Nov 16 #Python
详解python os.path.exists判断文件或文件夹是否存在
Nov 16 #Python
Python 删除List元素的三种方法remove、pop、del
Nov 16 #Python
python 从list中随机取值的方法
Nov 16 #Python
python实现在列表中查找某个元素的下标示例
Nov 16 #Python
python如何获得list或numpy数组中最大元素对应的索引
Nov 16 #Python
Python实现列表索引批量删除的5种方法
Nov 16 #Python
You might like
PHP 伪静态隐藏传递参数名的四种方法
2010/02/22 PHP
PHP json格式和js json格式 js跨域调用实现代码
2012/09/08 PHP
PHP根据传入参数合并多个JS和CSS文件的简单实现
2014/06/13 PHP
php魔术函数__call()用法实例分析
2015/02/13 PHP
PHP中set_include_path()函数相关用法分析
2016/07/18 PHP
PHP常见字符串处理函数用法示例【转换,转义,截取,比较,查找,反转,切割】
2016/12/24 PHP
javascript中的prototype属性实例分析说明
2010/08/09 Javascript
读jQuery之六 缓存数据功能介绍
2011/06/21 Javascript
jQuery实现简单下拉导航效果
2015/09/07 Javascript
JavaScript 性能优化小结
2015/10/12 Javascript
jQuery弹出层后禁用底部滚动条(移动端关闭回到原位置)
2016/08/29 Javascript
详解微信开发中snsapi_base和snsapi_userinfo及静默授权的实现
2017/03/11 Javascript
angularJS深拷贝详解
2017/03/23 Javascript
在vscode里使用.vue代码模板的方法
2018/04/28 Javascript
vue实现个人信息查看和密码修改功能
2018/05/06 Javascript
jquery3和layui冲突导致使用layui.layer.full弹出全屏iframe窗口时高度152px问题
2019/05/12 jQuery
Vue formData实现图片上传
2019/08/20 Javascript
小程序使用watch监听数据变化的方法详解
2019/09/20 Javascript
[54:15]DOTA2-DPC中国联赛 正赛 DLG vs Dragon BO3 第二场2月1日
2021/03/11 DOTA
python显示天气预报
2014/03/02 Python
Python中单例模式总结
2018/02/20 Python
解决python大批量读写.doc文件的问题
2018/05/08 Python
用python3教你任意Html主内容提取功能
2018/11/05 Python
python opencv 批量改变图片的尺寸大小的方法
2019/06/28 Python
Python中pass的作用与使用教程
2020/11/13 Python
全球知名旅游社区法国站点:TripAdvisor法国
2016/08/03 全球购物
Roxy荷兰官方网站:冲浪、滑雪板、服装和配件
2019/10/22 全球购物
传统软件工程与面向对象的软件工程有什么区别
2012/05/31 面试题
酒吧总经理岗位职责
2013/12/10 职场文书
公司庆典活动邀请函
2014/01/09 职场文书
运动会跳远加油稿
2014/02/20 职场文书
毕业生简历自我评价范文
2014/04/09 职场文书
爱岗敬业演讲稿
2014/05/05 职场文书
幼儿园小班个人工作总结
2015/02/12 职场文书
家长对学校的意见和建议
2015/06/03 职场文书
详解Alibaba Java诊断工具Arthas查看Dubbo动态代理类
2022/04/08 Java/Android