1

So I've been trying to find ways to play mp4 or videos in general in pygame and cant really find anything that works apart from opencv-python. I Have managed to play the video but it's very laggy and choppy so i tried to first read the video and save the frames inside a list then play the video But then the video still turned out to be very choppy?

import pygame
from pygame.locals import *
import cv2
import numpy as np
import sys
import threading

pygame.init()
pygame.display.set_caption("OpenCV video stream on Pygame")
surface = pygame.display.set_mode([1280,720])
video = cv2.VideoCapture("YouTube.mp4")
fps = video.get(cv2.CAP_PROP_FPS)
print(fps)
video.set(cv2.CAP_PROP_FPS, 60)

vid = []

clock = pygame.time.Clock()
print(clock)
def vid_cap():
    while True:
        success, frame = video.read()
        if not success:
            break

        #for some reasons the frames appeared inverted
        frame = np.fliplr(frame)
        frame = np.rot90(frame)

        # The video uses BGR colors and PyGame needs RGB
        frame = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)

        vid.append(frame)

#cap = threading.Thread(target = vid_cap)
#cap.start()
vid_cap()
try:
    while True:

        clock.tick(60)
        surface.fill([0,0,0])
        try:
            surf = pygame.surfarray.make_surface(vid[0])
            vid.pop(0)

            for event in pygame.event.get():
                if event.type == pygame.KEYUP:
                    background_color = red
                    surface.fill(background_color)
                    pygame.display.update
                    end_time = self.time()

            # Show the PyGame surface!
            surface.blit(surf, (0,0))
            pygame.display.flip()
        except:
            surface.fill([255,255,255])



except SystemExit:
    pygame.quit()
    cv2.destroyAllWindows()

YouTube.mp4 can be any 60 fps video you got

Elpupper
  • 46
  • 1
  • 12
  • What does `video.set( cv2.CAP_PROP_FPS, 60 )` do to the decoding? Are you (potentially) up-speeding everything to 60 FPS? – Kingsley Jun 17 '20 at 00:20
  • I played around with this a bit. Using the threaded-decode, on a full-HD 30FPS video, it was somewhat OK with the decoder going faster than playback. On a 4k 60FPS video it almost never kept up. I'm wondering if moving the decode to a separate process, and reading the frames over shared memory ( or just a pipe ) might work more smoothly as Python never needs to "time slice" between two threads, and your decoder gets its own core (or suchlike). – Kingsley Jun 17 '20 at 02:06
  • If you're not bound to the `cv2` module, there is another method using a stream decoded by `ffmpeg` - https://stackoverflow.com/a/58983459/1730895 – Kingsley Jun 17 '20 at 05:59
  • @Kingsley thank you very much I think ill look into ffmpeg to see if its any better :) – Elpupper Jun 17 '20 at 07:59
  • @Kingsley im not upspeeding the recording the video was already at 720p 60 fps but it wasnt displaing at 60 fps on my app – Elpupper Jun 17 '20 at 08:48

0 Answers0