python MP4视频转GIF动图
- 引言
- 一、转换代码
- 二、PyQt界面编写
- 2.1 效果展示
- 2.2 源码
- 三、打包成可执行文件(.exe)
一个相当于原视频三倍速的GIF动图
引言
将MP4格式的视频转为GIF动图可以方便地向他人展示动画效果
。GIF是网络上广泛使用的图像格式之一,几乎所有的网页浏览器和客户端都支持,其兼容性较好。比如可以直接插入到PPT中、或是在微信上发给别人、或者直接插入到CSDN博客中
,但是MP4等视频格式的文件显然不行。
常用的免费在线转换网站上不去了,好多其它网站需要注册,本作者亲自写一个方便日常使用。
当然,GIF也有其缺点,将MP4视频同帧率转为GIF,文件会变大,占用更多内存:
文心一言给出的理由:将MP4视频转换为GIF后,文件变大主要是因为GIF格式的编码方式和MP4不同。MP4文件内一般采用视频压缩的格式,例如h264,这种压缩方式利用时间上相邻两帧的相似性和人眼视觉上的冗余来做有损压缩,从而压缩率很高。而GIF格式则单独保留了每一帧图片,同时每张图片都是采用无损压缩的方式,因此GIF尺寸比较大。
一、转换代码
使用moviepy
库,安装: pip install moviepy
英文文档:https://zulko.github.io/moviepy/ 推荐,方便Search
中文文档:http://doc.moviepy.com.cn/
from moviepy.editor import *
myClip = VideoFileClip("xxx.mp4")
myClip.write_gif("xxx.gif")
write_gif默认与原视频时常一样(只能更改帧速率,默认帧率也与原视频一样),如果想更改播放速度可使用speedx
函数,如:
- 放慢一半:
myClip.speedx(0.5).write_gif("xxx.gif")
- 二倍速播放
myClip.speedx(2).write_gif("xxx.gif")
- write_gif参数官方解释:write_gif(self, filename, fps=None, program=‘imageio’, opt=‘nq’, fuzz=1, verbose=True, loop=0, dispose=False, colors=None, tempfiles=False, logger=‘bar’)
- write_gif参数解释:moviepy音视频剪辑基类VideoClip的write_gif方法opt、fuzz、dispose、colors、loop等参数的作用
- 转换代码也可参考: 使用Opencv将MP4文件转GIF图片
二、PyQt界面编写
2.1 效果展示
使用gif展示了一个将mp4转为gif动图的软件
2.2 源码
使用pyqt5-tool生成的ui界面,转成py后增加了mp4_to_gif
函数,可直接运行
# -*- coding: utf-8 -*-
from PyQt5 import QtCore, QtGui, QtWidgets
from PyQt5.QtWidgets import *
from PyQt5.QtCore import *
def mp4_to_gif():
dialog = QFileDialog()
dialog.setFileMode(QFileDialog.ExistingFile)
dialog.setAcceptMode(QFileDialog.AcceptOpen)
filename, _ = dialog.getOpenFileName(dialog, "Open file", "", "files (*.mp4);;(*.*)")
print(filename.replace('.mp4', '.gif'))
from moviepy.editor import VideoFileClip
myClip = VideoFileClip(filename)
myClip.speedx(3).write_gif(filename.replace('.mp4', '.gif'))
pass
class Ui_MainWindow(object):
def setupUi(self, MainWindow):
MainWindow.setObjectName("MainWindow")
MainWindow.resize(321, 71)
MainWindow.setMaximumSize(QtCore.QSize(321, 71))
self.centralwidget = QtWidgets.QWidget(MainWindow)
self.centralwidget.setObjectName("centralwidget")
self.pushButton = QtWidgets.QPushButton(self.centralwidget)
self.pushButton.setGeometry(QtCore.QRect(0, 0, 321, 71))
font = QtGui.QFont()
font.setFamily("微软雅黑")
font.setPointSize(24)
self.pushButton.setFont(font)
self.pushButton.setObjectName("pushButton")
MainWindow.setCentralWidget(self.centralwidget)
self.retranslateUi(MainWindow)
QtCore.QMetaObject.connectSlotsByName(MainWindow)
def retranslateUi(self, MainWindow):
_translate = QtCore.QCoreApplication.translate
MainWindow.setWindowTitle(_translate("MainWindow", "MP4_to_GIF"))
self.pushButton.setText(_translate("MainWindow", "将MP4转为GIF"))
# 按钮事件
self.pushButton.clicked.connect(mp4_to_gif)
if __name__ == "__main__":
import sys
app = QtWidgets.QApplication(sys.argv)
MainWindow = QtWidgets.QMainWindow()
ui = Ui_MainWindow()
ui.setupUi(MainWindow)
MainWindow.show()
sys.exit(app.exec_())
- 还有个小bug,filename为空,程序会奔溃
三、打包成可执行文件(.exe)
安装pyinstaller:pip install pyinstaller
- 执行
pyinstaller -F -w main.py
- 打包生成100MB的exe文件… 结果如下: