当前位置: 首页 > 工具软件 > MoviePy > 使用案例 >

python 速度 moviepy_python视频处理库:moviepy 第二篇

呼延沈义
2023-12-01

moviepy底层使用ffmpeg读取和导出视频以及音频文件。它使用ImageMagic对视频插入文字以及生成GIF(可选)。对于不同的媒体文件的处理是通过python高效的数值计算库numpy来完成的。一些特效处理等使用到了python的图像处理库比如PIL,scikit-images以及科学计算库scipy等。

关于moviepy的一些基础概念。moviepy的核心概念是clips,可以是AudioCLips 和 VideoClips 。这些clips可以被修改(剪切,降低播放速度,调整亮度等)或者和其他的clips混合到一起组成新的clips。然后这些clips可以通过pygame或者Ipython(jupyter notebook)预览,或者导出为videos文件或者GIF。VideoClips可以通过一个视频文件,图像文件或者文字以及动画来创建,这些VideoClips还可以有音轨(audio track)即 AudioCLips以及mask(这种一种特殊的VideoClips,当其他的clips混合在一起的时候,这个mask决定哪些clips可以显示出来)。具体操作下面我们主要以代码的形式展示。

Sample Code – clip_array的使用

#!/usr/bin/env python3

# encoding: utf-8

“””

@version: 0.1

@author: lyrichu

@license: Apache Licence

@contact: 919987476@qq.com

@site: http://www.github.com/Lyrichu

@file: clip_array.py

@time: 2018/05/19 14:38

@description:

stacking is done by clips_array

“””

from moviepy.editor import VideoFileClip,clips_array,vfx

clip1 = VideoFileClip(“sources/xq.mp4”).margin(10) # 增加10piexl的边框

clip2 = clip1.fx(vfx.mirror_x) # 水平翻转

clip3 = clip1.fx(vfx.mirror_y) # 垂直翻转

# downsize to 60% size

clip4 = clip1.resize(0.6)

# stack all videos together like arrays

final_clip = clips_array([[clip1,clip2],

[clip3,clip4]

]

)

final_clip.resize(width=480).write_videofile(“sources/stack.mp4”)

Sample Code – CompositeVideoClips

#!/usr/bin/env python3

# encoding: utf-8

“””

@version: 0.1

@author: lyrichu

@license: Apache Licence

@contact: 919987476@qq.com

@site: http://www.github.com/Lyrichu

@file: CompositeVideoClips.py

@time: 2018/05/19 14:51

@description:

CompositeVideoClip class,play sevral videos together

“””

from moviepy.editor import VideoFileClip,CompositeVideoClip

clip1 = VideoFileClip(“sources/xq.mp4”)

clip2 = VideoFileClip(“sources/girl.mp4”).set_position(“left”).set_start(3).crossfadein(1)

clip3 = VideoFileClip(“sources/dogs.mp4”).set_position(“right”).set_start(6).crossfadein(2)

final_clip = CompositeVideoClip([clip1,clip2,clip3])

final_clip.write_videofile(“sources/composite.mp4”)

上面的代码还是将三个clip组合到一起形成一个新的clip,只不过这次对每一个clip都做了一些操作,比如上面的 set_start 方法就是设置视频开始播放的时间, set_position 是设置clip的位置, crossfadein 是设置连接视频渐变的时间,还有很多其他的方法可以具体参考文档,使用这些方法,我们就可以将视频剪辑的更加丰富多彩,符合我们的要求。

Sample Code – Compositing audio clips

#!/usr/bin/env python3

# encoding: utf-8

“””

@version: 0.1

@author: lyrichu

@license: Apache Licence

@contact: 919987476@qq.com

@site: http://www.github.com/Lyrichu

@file: set_methods.py

@time: 2018/05/19 15:16

@description:

set_xxx methods

“””

from moviepy.editor import VideoFileClip,AudioFileClip,vfx

clip = VideoFileClip(“sources/xq.mp4”)

# create a audio clip

aclip = AudioFileClip(“sources/22.mp3”).subclip(50,55)

aclip.write_audiofile(“sources/22_clip.mp3”)

# 设置音频

clip = clip.set_audio(aclip) # 注意一定要赋值,否则不会有任何改变

# 1s 以后开始

clip = clip.set_start(1)

# 设置持续时间为3s

clip = clip.set_duration(3)

clip.write_videofile(“sources/set_xq.mp4”)

# 设置宽度,设置颜色变为更暗,速度变为原来的两倍

clip1 = clip.fx(vfx.resize,width=360).fx(vfx.colorx,0.5).fx(vfx.speedx,2)

clip1.write_videofile(“sources/xq1.mp4”)

上面的代码逻辑不难理解。首先构建了一个 VideoClip 对象,然后使用 subclip 方法截取音频50-55秒,然后保存为新的音频文件。接着对视频clip对象采用 set_audio 方法设置audio track,这里需要注意的是clip的很多方法都是采用”流式”操作,即 clip.set_xxx 放回的仍然是一个clip,因此可以连续使用set_xxx方法,所以需要注意使用set_xxx之后需要将结果保存到一个新的对象,否则设置是无效的。最后需要注意 clip.fx 是通用的设置clip的方法,具体用法可以查看文档。

Sample code – Create custom effects

#!/usr/bin/env python3

# encoding: utf-8

“””

@version: 0.1

@author: lyrichu

@license: Apache Licence

@contact: 919987476@qq.com

@site: http://www.github.com/Lyrichu

@file: change_attribute.py

@time: 2018/05/19 15:43

@description:

change video attribute

“””

from moviepy.editor import VideoFileClip

from math import sin

clip = VideoFileClip(“sources/xq.mp4”)

# make video 3 times faster

clip1 = clip.fl_time(lambda x:3*x).set_duration(3)

# 按照正弦timeline 播放,视频播放会非常抖动

clip2 = clip.fl_time(lambda x:1+sin(x)).set_duration(3)

clip1.write_videofile(“sources/xq2.mp4”)

clip2.write_videofile(“sources/xq3.mp4”)

def invert_green_blue(image):

”’

将图片的green channel 和 blue channel 转换

:param image: input image

:return: new image

”’

return image[:,:,[0,2,1]]

clip3 = clip.fl_image(image_func=invert_green_blue)

clip3.write_videofile(“sources/xq4.mp4”)

def scroll(get_frame, t):

“””

This function returns a ‘region’ of the current frame.

The position of this region depends on the time.

“””

frame = get_frame(t)

frame_region = frame[int(20*t):int(20*t)+100,:] # 得到部分区域

return frame_region

clip4 = clip.fl(fun=scroll)

clip4.write_videofile(“sources/xq5.mp4”)

上面的代码展示了如何使用clip的 fl 和 fl_time 以及 fl_image 方法来生成一些特效。

fl_time方法接收一个函数,对video的时间轴进行修改,该函数接收的是视频的时间属性t,所以上面的clip.fl_time(lambda x:3*x) 会让视频的播放速度加快3倍,而

clip.fl_time(lambda x:1+sin(x)) 则让视频按照正弦的timeline播放,视频会有些抖动。 fl_image 对视频每一帧图像进行修改,其接收的也是一个函数作为参数,该函数的参数为image(ndarray),所以上面的 invert_green_blue 函数做的工作就是将图片的green channel 和 blue channel 转换。而 fl函数是一个更一般的函数,其也是接收一个函数作为参数,该函数的参数有两个,一个是 get_frame 函数,一个是当前帧的时间t,函数需要返回一个image(ndarray),而不难看出上面的scroll 函数就是让视频随着时间的变化在水平方向向下移(展示图片的一部分,高度始终不变),在竖直方向上不改变。

Sample Code –

make videos from list of images

#!/usr/bin/env python3

# encoding: utf-8

“””

@version: 0.1

@author: lyrichu

@license: Apache Licence

@contact: 919987476@qq.com

@site: http://www.github.com/Lyrichu

@file: ImageSequenceClip.py

@time: 2018/05/19 17:15

@description:

create videos or gif from sequences of images

“””

import numpy as np

from glob import glob

from PIL import Image

from scipy.misc import imresize,imsave

imgs = glob(“sources/images/*.jpg”)

def preprocess_imgs(imgs,size = (900,1200)):

”’

把所有的图片resize成相同大小

:param imgs: list of images names

:param size: resized size

:return: None

”’

for img in imgs:

m = np.array(Image.open(img))

m = imresize(m,size)

imsave(img,m)

preprocess_imgs(imgs)

from moviepy.editor import ImageSequenceClip

clip = ImageSequenceClip(imgs,fps=2)

# export gif

clip.write_gif(“sources/xq_new.gif”)

不难发现,使用 ImageSequenceClip更为简单一点,但是要求所有的图片必须具有相同的大小,上面的 preprocess_imgs函数就是将所有的图片resize成相同的大小。

** 如果此篇文章有帮助到你,欢迎点击下方/页面上任意广告,支持我们,谢谢!

 类似资料: