MoviePy是一个用于视频编辑的Python模块,它可被用于一些基本操作(如剪切、拼接、插入标题)、视频合成(即非线性编辑)、视频处理和创建高级特效。它可对大多数常见视频格式进行读写,包括GIF。
示例如下(IPython Notebook环境)
用户手册
下载与安装
安装
pip安装方式:如果你安装了pip
,只需要在终端输入如下命令(若没有安装ez_setup,则会自动安装)
(sudo) pip install moviepy
如果你既没有安装setuptools
也没有安装ez_setup
,那么上述命令就会运行失败。在这种情况下,你需要在安装前运行:
(sudo) pip install ez_setep
手动安装方式:从 PyPI 或者 Github (开发版本)上下载源码。将所有文件解压到同一文件夹,打开终端并输入
(sudo) python setup.py install
MoviePy依赖 Numpy 、 imageio 、 Decorator 和 tqdm ,他们将在安装MoviePy的同时自动安装。运行平台为Windows/Mac/Linux,并使用Python2.7以上的版本和Python3。如果在安装MoviePy及其依赖包的过程中存在问题,请提供反馈。
MoviePy依赖FFMPEG软件对视频进行读写。不用对此担心,在你第一次使用MoviePy的时候,FFMPEG将会自动由ImageIO下载和安装(不过需要花一些时间)。如果你想使用FFMPEG的特定版本,你可以设置FFMPEG_BINARY环境变量。详见moviepy/config_defaults.py
。
可选但有用的依赖包
ImageMagick 只有在你想要添加文字时需要用到。它可作为一个后端用在GIF上,但如果不安装ImageMagick,你也可以用MoviePy处理GIF。
一旦你安装了ImageMagick,它会被MoviePy自动检测到,除了Windows环境! Windows用户在手动安装MoviePy之前,应在moviepy/config_defaults.py
文件中指定ImageMagick binary的路径,并叫做convert。看起来应该像是这样:
IMAGEMAGICK_BINARY = "C:\\Program Files\\ImageMagick_VERSION\\convert.exe"
你也可以设置IMAGEMAGICK_BINARY环境变量,详见moviepy/config_defaults.py
。
PyGame 在视频和声音预览中会使用到。不过如果你想要在服务器上使用MoviePy,但的确需要手动进行高级的视频编辑,Pygame就没什么用处啦。
对于高级的图片处理,你至少需要一个以下所列的包。例如使用clip.resize
方法,就至少需要安装Scipy、PIL、Pillow或OpenCV其中一个。
- Python图片库(PIL)或它的分支 Pillow 更好。
- Scipy (用于追踪、分割等)可在没有安装PIL和OpenCV的情况下用于调整视频剪辑的大小。
- Scikit Image 可能被用于高级的图片处理。
-
OpenCV 2.4.6 或更高版本(在
cv2
包中提供)可能被用于高级的图片处理。
如果你使用linux,这些软件都一定在你的仓库中。
MoviePy入门
此页面为你讲解如何使用MoviePy进行编辑。想了解更多的话,详阅作品展示和脚本示例。
快速准备
这个章节说明了使用MoviePy的场合以及工作原理。
我需要MoviePy吗?
这些是你想用Python编辑视频的理由:
- 你需要用很复杂的方法来处理或组成大量的视频;
- 你想在web服务器(Django、Flask等)自动生成视频或GIF动图;
- 你想自动完成无聊的任务,如插入标题、追踪对象、剪切场景、制作结尾的演职人员表、字幕等等;
- 你想用代码实现视频编辑软件所不能达到的视频效果;
- 你想将从别的Python库里(如Matplotlib、Mayavi、Gizeh、scikit-images等)生成的图片制作成动画。
但在以下情况中,MoviePy并非最好的选择:
- 你只需要对视频进行逐帧分析(如人脸识别或其他有趣的东西),使用MoviePy和别的库可以联合完成。但是事实上,仅使用 imageio、 OpenCV 或者SimpleCV这些专用库即可达到要求。
- 你只需要视频文件转换,或者将一系列图片文件转换成视频。在这种情况下,直接调用ffmpeg(或avconv、mencoder等)将比使用MoviePy更快速、更有效率地使用内存。
优势与局限性
MoviePy在以下方面表现出色:
- 易于上手:一行即可完成一项基本操作。对于新手来说,代码易学易懂。
- 灵活:视频和音频的每一帧都尽在掌握,创作属于自己的特效就像Python一样简单。
- 便携:代码使用十分常见的软件(Numpy和FFMPEG),而且可以在几乎所有版本的Python和几乎所有的机器上运行。
局限性:MoviePy目前还无法对流媒体进行处理(从摄像头或者远程设备获取视频),并且MoviePy并不是被设计成用来对电影的连续帧进行处理(例如视频去抖,你需要寻找另外的软件)。如果你同时处理大量视频,音频以及图片序列(数量大于100)可能会出现内存问题,但是这个问题会在将来的版本当中进行修复。
代码示例
在典型的MoviePy脚本是这样的:加载视频或音频、修改、将他们连接在一起并最后生成一个新视频文件。作为一个示例,我们加载一个关于我上个假期的视频,降低音量,在前十秒添加标题在视频的中央,然后写入一个文件:
# Import everything needed to edit video clips
from moviepy.editor import *
# Load myHolidays.mp4 and select the subclip 00:00:50 - 00:00:60
clip = VideoFileClip("myHolidays.mp4").subclip(50,60)
# Reduce the audio volume (volume x 0.8)
clip = clip.volumex(0.8)
# Generate a text clip. You can customize the font, color, etc.
txt_clip = TextClip("My Holidays 2013",fontsize=70,color='white')
# Say that you want it to appear 10s at the center of the screen
txt_clip = txt_clip.set_pos('center').set_duration(10)
# Overlay the text clip on the first video clip
video = CompositeVideoClip([clip, txt_clip])
# Write the result to a file (many options available !)
video.write_videofile("myHolidays_edited.webm")
MoviePy的工作原理
MoviePy使用ffmpeg
软件来读取和导出视频和音频文件。也使用(可选)ImageMagick来生成文字和制作GIF文件。不同媒体的处理依靠Python的快速的数学库Numpy。高级效果和增强功能使用一些Python的图片处理库(PIL,Scikit-image,scipy等)。
基本概念
在MoviePy中,核心对象是剪辑,可以使用AudioClips
或VideoClips
来处理。剪辑可被修改(剪切、降低速度、变暗等)或与其他剪辑混合组成新剪辑。剪辑可被预览(使用PyGame或IPython Notebook),也可生成文件(如MP4文件、GIF文件、MP3文件等)。以VideoClips
为例,它可以由一个视频文件、一张图片、一段文字或者一段卡通动画而来。它可以包含音频轨道(即AudioClip
)和一个遮罩(一种特殊的VideoClip
),用于表明当两个剪辑混合时,哪一部分的画面被隐藏)。详见生成与导出视频剪辑和混合剪辑。
你可使用MoviePy的很多效果对一个剪辑进行修改(如clip.resize(width="360")
、clip.subclip(t1,t2)
、clip.fx(vfx.black_white)
或使用用户自行实现的效果。MoviePy提供许多函数(如clip.fl、clip.fx等),可以用简单的几行代码实现你自己的效果。详见视频转换与效果。
你还可以在moviepy.video.tools找到一些高级的效果来对视频中的对象进行追踪、画简单的形状和颜色渐变(对于遮罩来说很有用)、生成字幕和结束时的演职人员表等。参见高级工具中的详细描述。
最后,尽管MoviePy没有生动的用户界面,它也有许多方法来预览剪辑,使你能够调试脚本,从而确保你的视频在高质量的同时一切正常。详见如果更有效率地使用MoviePy。
混合剪辑
视频合成,也称为非线性编辑,事实上就是把许多视频剪辑放在一起,变成一个新剪辑。这个视频就是一个很好的例子,告诉你可以用MoviePy做些什么样的合成:
原视频链接已失效
在开始之前要注意,一般来说视频剪辑都会带有音轨和遮罩,他们也同样是剪辑。当你将这些剪辑组合在一起时,音轨和剪辑的遮罩将会自动生成音轨和最终剪辑的遮罩。所以在大多数情况下,你并不必为混合音频和遮罩担心。
堆叠和连接剪辑
有两种简单的方法能将剪辑放在一起:一是连接(使它们变成一个更长的剪辑,一个接一个播放),二是堆起来(使他们并排组成画面更大的剪辑)。
使用concatenate_videoclips
函数进行连接操作。
from moviepy.editor import VideoFileClip, concatenate_videoclips
clip1 = VideoFileClip("myvideo.mp4")
clip2 = VideoFileClip("myvideo2.mp4").subclip(50,60)
clip3 = VideoFileClip("myvideo3.mp4")
final_clip = concatenate_videoclips([clip1,clip2,clip3])
final_clip.write_videofile("my_concatenation.mp4")
final_clip
是一个剪辑,使clip 1、2和3一个接一个播放。注意,剪辑不一定必须要相同尺寸。如果各剪辑尺寸不同,那么它们将被居中播放,而画面大小足够包含最大的剪辑,而且你可以选择一种颜色来填充边界部分。你还有许多其它可选项(详见函数的文档),例如你可以通过transition=my_clip
选项来在剪辑之间加一个过场。
使用clip_array
函数对剪辑进行堆叠操作。
from moviepy.editor import VideoFileClip, clips_array, vfx
clip1 = VideoFileClip("myvideo.mp4").margin(10) # add 10px contour
clip2 = clip1.fx( vfx.mirror_x)
clip3 = clip1.fx( vfx.mirror_y)
clip4 = clip1.resize(0.60) # downsize 60%
final_clip = clips_array([[clip1, clip2],
[clip3, clip4]])
final_clip.resize(width=480).write_videofile("my_stack.mp4")
从而你可以获得一个看起来是这样的剪辑:
合成视频剪辑
CompositeVideoClip类提供了一个非常灵活的方法来合成剪辑,但它比concatenate_videoclips
和clips_array
更复杂一些。
video = CompositeVideoClip([clip1,clip2,clip3])
当前video
播放clip1
,clip2
在clip1
的上层,而clip3
在clip1
和clip2
的上层。举例来说,如果clip2
与clip3
和clip1
有同样的尺寸,那么只有在顶层的clip3
能在视频中可见,除非clip3
和clip2
被遮罩隐藏了一部分。注意,在默认情况下,合成的视频和第一个剪辑的尺寸相同(因为它通常是一个背景)。但是有时,你想让你的剪辑在更大的合成视频里浮动,所以你需要像这样特意修改最终合成视频的尺寸:
video = CompositeVideoClip([clip1,clip2,clip3], size=(720,460))
起始和终止时间
在一个合成剪辑中,所有的剪辑开始的时间都被clip.start
属性所指定。你可以像这样设定开始时间:
clip1 = clip1.set_start(5) # start after 5 seconds
例如你的剪辑看起来会是这样:
video = CompositeVideoClip([clip1, # starts at t=0
clip2.set_start(5), # start at t=5s
clip3.set_start(9)]) # start at t=9s
在上面的例子中,clip2
可能先于clip1
的结束时间开始。在这种情况下,你可以给clip2
添加一个1秒钟的淡入效果:
video = CompositeVideoClip([clip1, # starts at t=0
clip2.set_start(5).crossfadein(1),
clip3.set_start(9).crossfadein(1.5)])
剪辑的定位
如果clip2
和clip3
都比clip1
小,你可以决定他们出现在视频中的位置。在这里,我们指定了剪辑左上角像素的坐标:
video = CompositeVideoClip([clip1,
clip2.set_pos((45,150)),
clip3.set_pos((90,100))])
有很多方法可以指定位置:
clip2.set_pos((45,150)) # x=45, y=150 , in pixels
clip2.set_pos("center") # automatically centered
# clip2 is horizontally centered, and at the top of the picture
clip2.set_pos(("center","top"))
# clip2 is vertically centered, at the left of the picture
clip2.set_pos(("left","center"))
# clip2 is at 40% of the width, 70% of the height of the screen:
clip2.set_pos((0.4,0.7), relative=True)
# clip2's position is horizontally centered, and moving down !
clip2.set_pos(lambda t: ('center', 50+t) )
当指定坐标的时候请记住,y
坐标的0位置在图片的最上方:
合成音频剪辑
当你将视频剪辑混合在一起时,MoviePy将会把它们各自的音轨自动合成为最终剪辑的音轨,所以不用担心需要自行合成音轨啦。 如果你想使用许多音频源来自定义音轨,可以使用CompositeAudioClip
和concatenate_audioclips
来进行混音。
from moviepy.editor import *
# ... make some audio clips aclip1, aclip2, aclip3
concat = concatenate_audioclips([aclip1, aclip2, aclip3])
compo = CompositeAudioClip([aclip1.volumex(1.2),
aclip2.set_start(5), # start at t=5s
aclip3.set_start(9)])
如何更有效率地使用MoviePy
这一节总结了一些技巧和诀窍,可以帮助你充分利用全球范围内已知的经验来使用MoviePy。
使用IPython Notebook是使用MoviePy的最好方法。它使得预览剪辑变得很容易(在此节中会介绍到),有自动完成功能,而且可以显示库里不同方法的文档。
我应该使用moviepy.editor
吗?
这篇文档里的大部分示例使用了moviepy.editor
子模块,但是这个子模块并不适用于所有需求。简单来说,如果你使用MoviePy手动编辑视频,那就建议使用此子模块;如果你在更大的库、更大的项目或web服务器上使用MoviePy,最好避免使用它,转而加载你需要的函数。
moviepy.editor
模块能以以下三种方式加载:
from moviepy.editor import * # imports everything, quick and dirty
import moviepy.editor as mpy # Clean. Then use mpy.VideoClip, etc.
from moviepy.editor import VideoFileClip # just import what you need
通过这些代码,moviepy.editor
模块会做许多幕后工作:它将获取MoviePy里最常见的类、函数和子包,初始化一个PyGame会话(在PyGame已安装的情况下)使得视频剪辑可被预览,并执行一些快捷方式,例如对剪辑添加resize
变换。以这种方式,你可以使用clip.resize(width=240)
来替代更长的clip.fx(resize,width=240)
写法。总之,moviepy.editor
提供了你所需要的播放和剪辑功能,但是需要一些时间来加载(大约1秒)。所以如果你所需要的一或两个效果在别的库里,直接将你所需要的导入是更好的选择,就像这样:
from moviepy.video.io.VideoFileClip import VideoFileClip
from moviepy.video.fx.resize import resize
预览剪辑的多种方法
当你使用MoviePy通过不断尝试来编辑视频或试图达到某种效果的时候,生成每个示例的视频的时间可能会很长。这一节提供了一些提高速度的小窍门。
clip.save_frame
很多时候,只需要视频中的一帧,即可说明你是否正确操作。你可以像这样保存剪辑中的一帧:
my_clip.save_frame("frame.jpeg") # saves the first frame
my_clip.save_frame("frame.png", t=2) # saves the frame a t=2s
clip.show and clip.preview
使用clip.show
和clip.preview
方法,使剪辑在Pygame的窗口中可视。这两个方法是预览的最快方法,当剪辑在生成和播放的同事,它们还可以获得坐标和像素的颜色。这些方法需要PyGame的支持,以及moviepy.editor
模块的使用。
clip.show
模块可以在没有写入文件的情况下预览剪辑里的一帧。如下是如何在PyGame窗口中显示一帧:
my_clip.show() # shows the first frame of the clip
my_clip.show(10.5) # shows the frame of the clip at t=10.5s
my_clip.show(10.5, interactive = True)
最后一行(有interactive=True
的一行)以一种交互的形式显示一帧:如果你单击这一帧的任意一处,它将输出位置和像素的颜色。当你结束查看时,按下esc键。
如下代码可预览剪辑:
my_clip.preview() # preview with default fps=15
my_clip.preview(fps=25)
my_clip.preview(fps=15, audio=False) # don't generate/play the audio.
my_audio_clip.preview(fps=22000)
如果你单击正在预览的视频剪辑中某帧的任意一处,将输出单击的位置和像素的颜色。按esc结束预览。
注意,如果剪辑很复杂而且你的电脑速度也不够快,剪辑的预览速度将会比真实速度慢。在这种情况下,你可以尝试降低帧率(例如将为10),或者用clip.resize
降低剪辑的尺寸。
ipython_display
使用IPython Notebook来显示剪辑很实用,尤其是你不想用clip.show()
和clip.preview()
时。看起来就像这样:
通过使用ipython_display
,你可以从文件或直接从片段里潜入视频、图片或声音:
ipython_display(my_video_clip) # embeds a video
ipython_display(my_imageclip) # embeds an image
ipython_display(my_audio_clip) # embeds a sound
ipython_display("my_picture.jpeg") # embeds an image
ipython_display("my_video.mp4") # embeds a video
ipython_display("my_sound.mp3") # embeds a sound
只有当ipython_display
在一个笔记本单元的最后一行才有效。你也可以调用ipython_display
作为一个剪辑方法:
my_video_clip.ipython_display()
如果对所呈现的视频的帧率有所要求,你可以在ipython_display
里指定fps=25
。
如果你只需要播放一个视频剪辑在时间t的快照,可以这样写:
my_video_clip.ipython_display(t=15) # will display a snapshot at t=15s
你还可以提供有效的HTML5选项作为关键词的参数。例如,如果剪辑太大,你可以这么写:
ipython_display(my_clip, width=400) # HTML5 will resize to 400 pixels
例如,当你编辑一个GIF动画,而且想检查它是否正确循环,你可以使视频自动启动和循环(即无限重复):
ipython_display(my_clip, autoplay=1, loop=1)
重要的是,ipython_display
实际上是将剪辑嵌入了你的笔记本里。优势在于你可以移动笔记本或将其放在网络上发布,视频将会运行。缺陷在于笔记本的文件尺寸会变得非常巨大。根据你的浏览器,多次重新计算和播放视频会在cache和RAM中占用一些空间(仅当密集使用时出现此问题)。重启浏览器即可解决问题。
使用matplotlib
自定义动画
MoviePy提供了一种生成自定义动画的方式:通过定义一个函数,以numpy数组的形式返回一个在给定的时间内一帧的动画。
例如,在如下的工作流中:
from moviepy.editor import VideoClip
def make_frame(t):
"""Returns an image of the frame for time t."""
# ... create the frame with any library here ...
return frame_for_time_t # (Height x Width x 3) Numpy array
animation = VideoClip(make_frame, duration=3) # 3-second clip
这个动画可以像通常一样导出:
# export as a video file
animation.write_videofile("my_animation.mp4", fps=24)
# export as a GIF
animation.write_gif("my_animation.gif", fps=24) # usually slower
matplotlib的简易实例
一个使用matplotlib的动画实例如下:
import matplotlib.pyplot as plt
import numpy as np
from moviepy.editor import VideoClip
from moviepy.video.io.bindings import mplfig_to_npimage
x = np.linspace(-2, 2, 200)
duration = 2
fig, ax = plt.subplots()
def make_frame(t):
ax.clear()
ax.plot(x, np.sinc(x**2) + np.sin(x + 2*np.pi/duration * t), lw=3)
ax.set_ylim(-1.5, 2.5)
return mplfig_to_npimage(fig)
animation = VideoClip(make_frame, duration=duration)
animation.write_gif('matplotlib.gif', fps=20)
在Jupyter Notebook中运行
如果你在Jupyter Notebook中运行,你可以体会到用ipython_display方法将视频剪辑嵌入在输出单元中的优势。示例如下:
import matplotlib.pyplot as plt
import numpy as np
from moviepy.editor import VideoClip
from moviepy.video.io.bindings import mplfig_to_npimage
x = np.linspace(-2, 2, 200)
duration = 2
fig, ax = plt.subplots()
def make_frame(t):
ax.clear()
ax.plot(x, np.sinc(x**2) + np.sin(x + 2*np.pi/duration * t), lw=3)
ax.set_ylim(-1.5, 2.5)
return mplfig_to_npimage(fig)
animation = VideoClip(make_frame, duration=duration)
animation.ipython_display(fps=20, loop=True, autoplay=True)
MoviePy的音频操作
这个章节会告诉你如何使用MoviePy去创建和编辑音频剪辑。
注意,当你使用MoviePy来剪切、混合或连接视频剪辑时,音频是自动处理的。如果你有兴趣来编辑音频文件,或者你想自定义视频的音频剪辑,请阅读此章。
音频剪辑的构成
在MoviePy中,音频剪辑和视频剪辑很相似:它们拥有长度,能以同样的方式被剪辑和组成,等等。一个显著的差异是audioclip.get_frame(t)
创建一个新的音频剪辑
音频剪辑可由一个音频文件创建,或从视频剪辑的音轨里提取出来。
from moviepy.editor import *
audioclip = AudioFileClip("some_audiofile.mp3")
audioclip = AudioFileClip("some_video.avi")
详见AudioFileClip
。
或者你也可以得到一个已创建的视频剪辑的音轨。
videoclip = VideoFileClip("some_video.avi")
audioclip = videoclip.audio
合成音频剪辑
导出和预览音频剪辑
你也可以导出分配一个音频剪辑当作视频剪辑的音轨。
videoclip2 = videoclip.set_audio(my_audioclip)
生成和导出视频剪辑
视频和音频剪辑是MoviePy里的核心对象。在此节里我们展示了如何生成不同种类的剪辑,以及如何将它们写入文件。关于修改剪辑信息(剪切、特效等),见视频转换与效果。关于如何将多个视频进行合成,见混合剪辑。关于如何在导出前预览视频,见如何更有效率地使用MoviePy。
下面的代码总结了你可以用MoviePy生成的剪辑基本类型。
# VIDEO CLIPS
clip = VideoClip(make_frame, duration=4) # for custom animations (see below)
clip = VideoFileClip("my_video_file.mp4") # or .avi, .webm, .gif ...
clip = ImageSequenceClip(['image_file1.jpeg', ...], fps=24)
clip = ImageClip("my_picture.png") # or .jpeg, .tiff, ...
clip = TextClip("Hello !", font="Amiri-Bold", fontsize=70, color="black")
clip = ColorClip(size=(460,380), color=[R,G,B])
# AUDIO CLIPS
clip = AudioFileClip("my_audiofile.mp3") # or .ogg, .wav... or a video !
clip = AudioArrayClip(numpy_array, fps=44100) # from a numerical array
clip = AudioClip(make_frame, duration=3) # uses a function make_frame(t)
视频剪辑的类型
长视频是由视频剪辑组成的。这些剪辑可以使用专门的clip.get_frame()
方法输出一个HxWx3的numpy数组来表示剪辑在时间t时的一帧。它们分为两类,一种是动态剪辑(由VideoFileClip
和VideoClip
组成),另一种是非动态剪辑,在任意无限长的持续时间中展示同一图片(ImageClip
、TextClip
、ColorClip
)。还有一种特殊的视频剪辑叫做遮罩,同属于上面的类别,但是输出灰度值帧以表示另一个剪辑里的可见部分。一个视频剪辑可以携带一个音频剪辑clip.audio
作为她的音轨,和一个遮罩剪辑。
VideoClip
VideoClip
是MoviePy中所有其它视频剪辑里最基本的种类。如果你只想编辑视频文件,你就永远不会用到它。当你想通过从别的库里生成的帧来生成动画时,这个类就会很有用。你需要做的只是定义一个make_frame(t)
函数,使它返回一个HxWx3的numpy数组(8位整数)来代表时间t时的帧。这里是一个使用制图库Gizeh的例子:
import gizeh
import moviepy.editor as mpy
def make_frame(t):
surface = gizeh.Surface(128,128) # width, height
radius = W*(1+ (t*(2-t))**2 )/6 # the radius varies over time
circle = gizeh.circle(radius, xy = (64,64), fill=(1,0,0))
circle.draw(surface)
return surface.get_npimage() # returns a 8-bit RGB array
clip = mpy.VideoClip(make_frame, duration=2) # 2 seconds
clip.write_gif("circle.gif",fps=15)
注意,剪辑使用make_frame并没有一个精确的帧速率,所以你必须要为write_gif
和write_videofile
,以及需要遍历每一帧的方法提供帧速率(fps
,每秒的帧数)。
VideoFileClip
视频文件剪辑是由视频文件(支持大多数格式)或GIF文件中读取的剪辑。你可以像这样加载一个视频:
myclip = VideoFileClip("some_video.avi")
myclip = VideoFileClip("some_animation.gif")
注意,这些剪辑都有fps
(帧速率)属性,当你对剪辑做小改动时,帧速率将会被传送,而且会以write_videofile
、write_gif
等的默认设置会使用。例如:
myclip = VideoFileClip("some_video.avi")
print (myclip.fps) # prints for instance '30'
# Now cut the clip between t=10 and 25 secs. This conserves the fps.
myclip2 = myclip.subclip(10, 25)
myclip2.write_gif("test.gif") # the gif will have 30 fps
详见VideoFileClip。
ImageSequenceClip
这是一种由一系列图片组成的剪辑,你可以这样调用:
clip = ImageSequenceClip(images_list, fps=25)
作品展示
脚本示例
移动的字母
我认为这个例子很好地展示了基于脚本编辑的有趣之处(想象是手动实现它的)。
代码如下:
import numpy as np
from moviepy.editor import *
from moviepy.video.tools.segmenting import findObjects
# WE CREATE THE TEXT THAT IS GOING TO MOVE, WE CENTER IT.
screensize = (720,460)
txtClip = TextClip('Cool effect',color='white', font="Amiri-Bold",
kerning = 5, fontsize=100)
cvc = CompositeVideoClip( [txtClip.set_pos('center')],
size=screensize)
# THE NEXT FOUR FUNCTIONS DEFINE FOUR WAYS OF MOVING THE LETTERS
# helper function
rotMatrix = lambda a: np.array( [[np.cos(a),np.sin(a)],
[-np.sin(a),np.cos(a)]] )
def vortex(screenpos,i,nletters):
d = lambda t : 1.0/(0.3+t**8) #damping
a = i*np.pi/ nletters # angle of the movement
v = rotMatrix(a).dot([-1,0])
if i%2 : v[1] = -v[1]
return lambda t: screenpos+400*d(t)*rotMatrix(0.5*d(t)*a).dot(v)
def cascade(screenpos,i,nletters):
v = np.array([0,-1])
d = lambda t : 1 if t<0 else abs(np.sinc(t)/(1+t**4))
return lambda t