python编辑视频字符化_Python 视频转字符画 - 进阶

这篇文章是 视频转字符动画-Python-60行代码 的后续,如果感兴趣,请先看看它。

0. 话说在前头

最新版使用了画布方式实现,和本文相比改动非常大,如果对旧版本的实现没啥兴趣,可以直接移步 video2chars,它的效果动画见 极乐净土。新版本的核心代码不算注释70行不到,功能更强大。

下面的效果动画是使用 html 实现的字符动画效果(上一篇的效果动画是 shell 版的):

本文的优化仍然是针对 shell 版本的,html 版由于缺陷太大就不写文章介绍了。

1. 速度优化

要是每次播放都要等个一分钟,也太痛苦了一点。

所以可以用 pickle 模块把 video_chars 保存下来,下次播放时,如果发现当前目录下有这个保存下来的数据,就跳过转换,直接播放了。这样就快多了。

只需要改一下测试代码,

先在开头添加两个依赖

import os

import pickle

然后在文件结尾添加代码:

def dump(obj, file_name):

"""

将指定对象,以file_nam为名,保存到本地

"""

with open(file_name, 'wb') as f:

pickle.dump(obj, f)

return

def load(filename):

"""

从当前文件夹的指定文件中load对象

"""

with open(filename, 'rb') as f:

return pickle.load(f)

def get_file_name(file_path):

"""

从文件路径中提取出不带拓展名的文件名

"""

# 从文件路径获取文件名 _name

path, file_name_with_extension = os.path.split(file_path)

# 拿到文件名前缀

file_name, file_extension = os.path.splitext(file_name_with_extension)

return file_name

def has_file(path, file_name):

"""

判断指定目录下,是否存在某文件

"""

return file_name in os.listdir(path)

def get_video_chars(video_path, size):

"""

返回视频对应的字符视频

"""

video_dump = get_file_name(video_path) + ".pickle"

# 如果 video_dump 已经存在于当前文件夹,就可以直接读取进来了

if has_file(".", video_dump):

print("发现该视频的转换缓存,直接读取")

video_chars = load(video_dump)

else:

print("未发现缓存,开始字符视频转换")

print("开始逐帧读取")

# 视频转字符动画

imgs = video2imgs(video_path, size)

print("视频已全部转换到图像, 开始逐帧转换为字符画")

video_chars = imgs2chars(imgs)

print("转换完成,开始缓存结果")

# 把转换结果保存下来

dump(video_chars, video_dump)

print("缓存完毕")

return video_chars

if __name__ == "__main__":

# 宽,高

size = (64, 48)

# 视频路径,换成你自己的

video_path = "BadApple.mp4"

video_chars = get_video_chars(video_path, size)

play_video(video_chars)

另一个优化方法就是边转换边播放,就是同时执行上述三个步骤。学会了的话,可以自己实现一下试试。

2. 字符视频和音乐同时播放

没有配乐的动画,虽然做出来了是很有成就感,但是你可能看上两遍就厌倦了。

所以让我们来给它加上配乐。(不要担心,其实就只需要添加几行代码而已)

首先我们需要找个方法来播放视频的配乐,怎么做呢?

先介绍一下一个跨平台视频播放器:mpv,它有很棒的命令行支持,请先安装好它。

要让 mpv 只播放视频的音乐部分,只需要命令:

mpv --no-video video_path

好了,现在有了音乐,可总不能还让人开俩shell,先放音乐,再放字符画吧。

这时候,我们需要的功能是:使用 Python 调用外部应用.

但是 mpv 使用了类似 curses 的功能,标准库的 os.system 不能隐藏掉这个部分,播放效果不尽如人意。

因此我使用了 pyinvoke 模块,只要给它指定参数hide=True,就可以完美隐藏掉被调用程序的输出(指 stdout,其实 subprocess 也可以的)。运行下面代码前,请先用pip安装好 invoke.(能够看到这里的,安装个模块还不是小菜一碟)

好了废话说这么多,上代码:

import invoke

video_path = "BadApple.mp4"

invoke.run(f"mpv --no-video {video_path}", hide=True, warn=True)

运行上面的测试代码,如果听到了音乐,而shell啥都没输出,但是能听到音乐的话,就正常了。我们继续。(这里使用了python3.6的f字符串)

音乐已经有了,那就好办了。

添加一个播放音乐的函数

import invoke

def play_audio(video_path):

invoke.run(f"mpv --no-video {video_path}", hide=True, warn=True)

然后修改main()方法:

def main():

# 宽,高

size = (64, 48)

# 视频路径,换成你自己的

video_path = "BadApple.mp4"

# 只转换三十秒,这个属性是才添加的,但是上一篇的代码没有更新。你可能需要先上github看看最新的代码。其实就稍微改了一点。

seconds = 30

# 这里的fps是帧率,也就是每秒钟播放的的字符画数。用于和音乐同步。这个更新也没写进上一篇,请上github看看新代码。

video_chars, fps = get_video_chars(video_path, size, seconds)

# 播放音轨

play_audio(video_path)

# 播放视频

play_video(video_chars, fps)

if __name__ == "__main__":

main()

然后运行。。并不是我坑你,你只听到了声音,却没看到字符画。。原因是: invoke.run()函数是阻塞的,音乐没放完,代码就到不了play_video(video_chars, fps)这一行。

所以 play_audio 还要改一下,改成这样:

import invoke

from threading import Thread

def play_audio(video_path):

def call():

invoke.run(f"mpv --no-video {video_path}", hide=True, warn=True)

# 这里创建子线程来执行音乐播放指令,因为 invoke.run() 是一个阻塞的方法,要同时播放字符画和音乐的话,就要用多线程/进程。

# P.S. 更新:现在发现可以用 subprocess.Popen 实现异步调用 mpv,不需要开新线程。有兴趣的同学可以自己试试。

p = Thread(target=call)

p.setDaemon(True)

p.start()

这里使用标准库的 threading.Thread 类来创建子线程,让音乐的播放在子线程里执行,然后字符动画还是主线程执行,Ok,这就可以看到最终效果了。实际上只添加了十多行代码而已。

3. 彩色字符动画

html+javascript 方式:核心都是一样的内容,只是需要点 html 和 javascript 的知识。代码见 video2chars-html

画布方式:直接把画在图片上,然后自动合成为 mp4 文件。这种方式要优于 html 方式,而且有个很方便的库能用,核心代码就 70 行的样子。代码见 video2chars

参考

python图像、视频转字符画

python图像转字符画需要用到matplotlib.pyplot库,视频转字符画需要用到opencv库,这里的代码基于python 3.5 图像转字符画需要先将图像转为灰度图,转灰度图的公式是 gr ...

Python 图片转字符画

Python 图片转字符画 一.课程介绍 1. 课程来源 原创 2. 内容简介 本课程讲述怎样使用 Python 将图片转为字符画 3. 前置课程 Python编程语言 Linux 基础入门(新版) ...

使用Python生成ASCII字符画

使用Python生成ASCII字符画 在很多的网站主页中或者程序的注释中会有一些好看的字符注释画.显得很牛逼的样子 例如: 知乎 _____ _____ _____ _____ /\ \ /\ \ / ...

[笔记] Python 图片转字符画

一.介绍 用Python 代码完成图片转字符画 二.python 环境 Python 3.6.6 pillow 5.1.0  Python 图像处理库, 需要另外安装 三.原理 gray = 0.21 ...

python图片转字符画(转)

先上代码: from PIL import Image import argparse #命令行输入参数处理 parser = argparse.ArgumentParser() parser.add ...

Python图片转字符画

PIL安装很麻烦,推荐下载exe直接安装 PIL官网:http://pythonware.com/products/pil/ 但现在里面下载链接访问不了,我把32位和64位版本上传到博客园以供下载 P ...

视频转字符动画-Python-60行代码

更新:2018-5-21 注意: 最后一步播放字符动画使用了只支持类 unix 系统的模块 curses, 因此在windows上是播放不了的... 解决方法: 1. 最近好像有一个移植 https: ...

python 图片在线转字符画预览

文章链接:https://mp.weixin.qq.com/s/yiFOmljhyalE8ssAgwo6Jw 关于python图片转字符画,相信大家都不陌生,经常出现在 n个超有趣的python项目中 ...

教程,Python图片转字符堆叠图

Python 图片转字符画 一.实验说明 1. 环境登录 无需密码自动登录, 2. 环境介绍 本实验环境采用带桌面的UbuntuLinux环境,实验中会用到桌面上的程序: LX终端(LXTermina ...

随机推荐

cocos2dx 3.x (单选,多选,复选checkBox按钮的实现) RadioButton

// //  LandLordsMakeNewRoom.hpp //  MalaGame39 // //  Created by work on 2016/12/19. // //   #ifndef ...

DOM – 7.动态创建DOM + 8.innerText innerHTML value

7.动态创建DOM 8.innerText  innerHTML  value 7+8 练习:案例:点击按钮动态增加网站列表,分两列,第一列为网站的名字,第二列为带网站超链接的网站名.增加三行常见网站 ...

Mac 自带 apache

1.启动服务器 sudo apachectl start http://localhost   能访问就ok sudo apachectl stop sudo apachectl restart ht ...

HTML+CSS学习笔记(9)- CSS的继承、层叠和特殊性

标签:HTML+CSS 继承 CSS的某些样式是具有继承性的,那么什么是继承呢?继承是一种规则,它允许样式不仅应用于某个特定html标签元素,而且应用于其后代.比如下面代码:如某种颜色应用于p标签,这 ...

java序列化/反序列化之xstream、protobuf、protostuff 的比较与使用例子

目录 背景 测试 环境 工具 说明 结果 结论 xstream简单教程 准备 代码 protobuf简单教程 快速入门 下载.exe编译器 编写.proto文件 利用编译器编译.proto文件生成ja ...

php Pthread 多线程 (二) Worker和Threaded

Oracle数据类型之nchar

nchar(size)  nvarchar2(size) n 代表的意思是编码格式为unicode编码,无论中文或者英文都以一个字符来存放数据. 举例: 比如“a” ,占用一个字符 比如“月”,占用一 ...

sysbench 0.4.12安装

前提:mysql已安装完成,请参考http://www.cnblogs.com/lizhi221/p/6813907.html   安装依赖环境包: yum install -y bzr yum in ...

PHP 基础篇 - PHP 正则官方文档汇总

一.PCRE 正则语法 下面是 PHP 的 PCRE 正则语法(模式语法)相关文档,详情请查阅相关链接: 简介 分隔符 元字符 转义序列(反斜线) Unicode字符属性 锚 句点 字符类(方括号) ...

L158

It started out modestly enough: David Hertz, having learned that under the right conditions you real ...

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值