Home > Back-end >  Write video frames to another video Python OpenCV
Write video frames to another video Python OpenCV

Time:10-23

I'm reading a video from YouTube(for testing purpose. real case would be from a video camera feed) and take each frame and inject a logo on it and create another video using those frames. Also I need to save these frames as images as well(which is already works for me). I tried the following,

img = cv2.imread('logo.png')
img_height, img_width, _ = img.shape
url = "https://www.youtube.com/watch?v=vDHtypVwbHQ"
video = pafy.new(url)
best = video.getbest(preftype="mp4")
frame_no = 1

width = 1280
hieght = 720
fps = 30
fourcc = cv2.VideoWriter_fourcc(*'mp4v')
videoW = cv2.VideoWriter('image_to_video.mp4', fourcc, float(fps), (width, hieght))

while True:
    _, frame = video.read()
    frame[y:y   img_height , x:x   img_width ] = img          
    videoW.write(frame)
    frame_no  = 1

This writes a video but it says the video corrupted or incorrect extension. What would be the best way to write these frames into a new video in Python with OpenCV?

CodePudding user response:

There are many illogical things in the implementation such as "video" is a pafy.Stream that does not have a read method.

What you should do use the Stream url together with VideoCapture to obtain the frames, copy the pixels of the logo, and write it with VideoWriter.

import cv2
import pafy


def apply_logo(url, logo, filename):
    video = pafy.new(url)
    best = video.getbest(preftype="mp4")
    reader = cv2.VideoCapture(best.url)
    if not reader.isOpened():
        return False

    fourcc = cv2.VideoWriter_fourcc(*"MP4V")
    writer = cv2.VideoWriter(filename, fourcc, 60.0, best.dimensions)

    logo_width, logo_height = [min(x, y) for x, y in zip(best.dimensions, logo.shape)]

    i = 0
    while True:
        ret, frame = reader.read()
        if ret:
            frame[:logo_width, :logo_height] = logo[:logo_width, :logo_height]
            writer.write(frame)
            i  = 1
            print(i)
        else:
            break

    reader.release()
    writer.release()
    return True

url = "https://www.youtube.com/watch?v=vDHtypVwbHQ"
logo = cv2.imread("logo.png")
apply_logo(url, logo, "output.mp4")
  • Related