利用Python和C#实现字符视频
一、准备
我们使用Python和C#
先确保安装了opencv和pillow
pip install opencv-python pip install pillow
二、 处理视频
将视频逐帧转换为图片,然后逐张读入,修改大小为64×48,再转换为灰度图,然后二值化保存
import cv2 import numpy as np from PIL import Image #高度48 宽度64 H = 48 W = 64 #总帧数 cnt = 0 print("Char video maker by Azure99\nPress Enter to continue") input() print("Reading video") video = cv2.VideoCapture("video.flv") while video.isOpened() : print("img%d" % cnt) r, img = video.read(); try : gary = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) except : break cv2.imwrite("png\\%d.png" % cnt, img) cnt += 1 videoData = open("video.txt", "w") #逐帧转换为字符图 for i in range(cnt): print("frame%d" % i) #读入图片并修改大小, 再转换为灰度图 img = Image.open("png\\%d.png" % i, "r").resize((W, H)).convert("L") for Y in range(H): for X in range(W): pixel = img.getpixel((X, Y)) #二值化 if pixel < 200: videoData.write(" #") else : videoData.write(" ") videoData.write("\n") videoData.close() print("All done!Now you can move video.txt to C# Player folder")
三、编写播放器
以48行为一帧,逐帧播放,并适当暂停
优化:
1.在播放前全部读入数据,并以每48行为单位保存在数组中
2.输出一帧时不要清屏,而是将光标移到开头,重新输出
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.IO; using System.Threading; namespace Player { class Program { private const int HEIGHT = 48;//每帧高度 private static string[] frames; static void Main(string[] args) { Console.WriteLine("\t\tReading video...\n\n"); ReadVideo(); Console.WriteLine("\t\tChar video player by Azure99\n\t\tPress any key to play"); Console.ReadKey(); PlayVideo(); } private static void ReadVideo() { StreamReader sr = new StreamReader("video.txt", Encoding.Default); List<string> framesList = new List<string>(); while (!sr.EndOfStream) { StringBuilder sb = new StringBuilder(); for(int i=0; i<HEIGHT; i++)//48行为一帧 { sb.Append(sr.ReadLine() + "\n"); } framesList.Add(sb.ToString()); } frames = framesList.ToArray(); } private static void PlayVideo() { Console.Clear(); for (int i = 0; i < frames.Length; i++) { //不要清屏, 将光标移到0, 0 Console.CursorLeft = 0; Console.CursorTop = 0; Console.Write(frames[i]); Thread.Sleep(30);//根据机器配置, 调整暂停时间 } } } }