Saving a video with text overlay in OpenCV

1

I wrote a script that records video from my webcam, writes text over it, and saves to disk. However, I can't seem to get it to work or the video to play in VLC.

Here's the script for trying all the codec / extension type combinations, which I run, hit ESC repeatedly, see if works in VLCs, and repeat for each combination until the script exits:

import cv2
import os

extensions = ['avi', 'mp4']
codecs = ['MJPG', 'H264', 'DIVX', 'XVID', 'X264']

for ext in extensions:
    for codec in codecs:
        savepath = "output__%s.%s" % (codec, ext)

        try:
            # setup up our webcam to read frames
            cap = cv2.VideoCapture(0)
            cap.set(cv2.CAP_PROP_FRAME_WIDTH, 1920)
            cap.set(cv2.CAP_PROP_FRAME_HEIGHT, 1080)

            # and our buffer to write frames
            fourcc = cv2.VideoWriter_fourcc(*codec)
            out = cv2.VideoWriter(savepath, fourcc, 20.0, (1080, 1920), 1)

            while True:
                ret, frame = cap.read()
                text = 'testing 123'
                font = cv2.FONT_HERSHEY_SIMPLEX
                cv2.putText(frame, text, (50, 50), font, 2, (255, 255, 0), 2)

                # write our frame
                out.write(frame)

                cv2.imshow('My Frame', frame)
                ch = cv2.waitKey(1)
                if ch == 27:  # ESC
                    break


            cap.release()
            out.release()
            cv2.destroyAllWindows()

            os.system("vlc %s" % savepath)

        except Exception as e:
            print "Combo codec=%s, exte=%s failed with: %s" % (codec, ext, str(e))

The results of running this script:

$ python test.py 
OpenCV Error: Assertion failed (img.cols == width && img.rows == height && channels == 3) in write, file /home/me/code/myproject/OpenCV-3.2.0/modules/videoio/src/cap_mjpeg_encoder.cpp, line 829
Combo codec=MJPG, exte=avi failed with: /home/me/code/myproject/OpenCV-3.2.0/modules/videoio/src/cap_mjpeg_encoder.cpp:829: error: (-215) img.cols == width && img.rows == height && channels == 3 in function write

VIDEOIO ERROR: V4L2: Pixel format of incoming image is unsupported by OpenCV
Unable to stop the stream: Device or resource busy
OpenCV Error: Assertion failed (size.width>0 && size.height>0) in imshow, file /home/me/code/myproject/OpenCV-3.2.0/modules/highgui/src/window.cpp, line 312
Combo codec=H264, exte=avi failed with: /home/me/code/myproject/OpenCV-3.2.0/modules/highgui/src/window.cpp:312: error: (-215) size.width>0 && size.height>0 in function imshow

init done
opengl support available

For codec=DIVX, extension=avi
VLC media player 2.2.2 Weatherwax (revision 2.2.2-0-g6259d80)
[0000000001f0e148] core libvlc: Running vlc with the default interface. Use 'cvlc' to use vlc without interface.
[00007eff1cc017d8] avi demux error: no key frame set for track 0
QObject::~QObject: Timers cannot be stopped from another thread

For codec=XVID, extension=avi
VLC media player 2.2.2 Weatherwax (revision 2.2.2-0-g6259d80)
[00000000022b8148] core libvlc: Running vlc with the default interface. Use 'cvlc' to use vlc without interface.
[00007f9c14c017d8] avi demux error: no key frame set for track 0
QObject::~QObject: Timers cannot be stopped from another thread

For codec=X264, extension=avi
VLC media player 2.2.2 Weatherwax (revision 2.2.2-0-g6259d80)
[0000000001a55148] core libvlc: Running vlc with the default interface. Use 'cvlc' to use vlc without interface.
[00007f485cc017d8] avi demux error: no key frame set for track 0
QObject::~QObject: Timers cannot be stopped from another thread
OpenCV: FFMPEG: tag 0x47504a4d/'MJPG' is not supported with codec id 8 and format 'mp4 / MP4 (MPEG-4 Part 14)'
OpenCV: FFMPEG: fallback to use tag 0x0000006c/'l???'

For codec=MJPG, extension=mp4
VLC media player 2.2.2 Weatherwax (revision 2.2.2-0-g6259d80)
[0000000000e53148] core libvlc: Running vlc with the default interface. Use 'cvlc' to use vlc without interface.
[00007f02a8c017d8] mp4 demux error: cannot find any /moov/trak
QObject::~QObject: Timers cannot be stopped from another thread
OpenCV: FFMPEG: tag 0x34363248/'H264' is not supported with codec id 28 and format 'mp4 / MP4 (MPEG-4 Part 14)'
OpenCV: FFMPEG: fallback to use tag 0x00000021/'!???'

For codec=H264, extension=mp4
VLC media player 2.2.2 Weatherwax (revision 2.2.2-0-g6259d80)
[00000000015f8148] core libvlc: Running vlc with the default interface. Use 'cvlc' to use vlc without interface.
[00007f6994c01838] mp4 demux error: cannot find any /moov/trak
QObject::~QObject: Timers cannot be stopped from another thread
OpenCV: FFMPEG: tag 0x58564944/'DIVX' is not supported with codec id 13 and format 'mp4 / MP4 (MPEG-4 Part 14)'
OpenCV: FFMPEG: fallback to use tag 0x00000020/' ???'

For codec=DIVX, extension=mp4
VLC media player 2.2.2 Weatherwax (revision 2.2.2-0-g6259d80)
[0000000001880148] core libvlc: Running vlc with the default interface. Use 'cvlc' to use vlc without interface.
[00007f21acc017d8] mp4 demux error: cannot find any /moov/trak
QObject::~QObject: Timers cannot be stopped from another thread
OpenCV: FFMPEG: tag 0x44495658/'XVID' is not supported with codec id 13 and format 'mp4 / MP4 (MPEG-4 Part 14)'
OpenCV: FFMPEG: fallback to use tag 0x00000020/' ???'

For codec=XVID, extension=mp4
VLC media player 2.2.2 Weatherwax (revision 2.2.2-0-g6259d80)
[000000000178c148] core libvlc: Running vlc with the default interface. Use 'cvlc' to use vlc without interface.
[00007f1e64c01858] mp4 demux error: cannot find any /moov/trak
QObject::~QObject: Timers cannot be stopped from another thread
OpenCV: FFMPEG: tag 0x34363258/'X264' is not supported with codec id 28 and format 'mp4 / MP4 (MPEG-4 Part 14)'
OpenCV: FFMPEG: fallback to use tag 0x00000021/'!???'

For codec=X264, extension=mp4
VLC media player 2.2.2 Weatherwax (revision 2.2.2-0-g6259d80)
[0000000000baa148] core libvlc: Running vlc with the default interface. Use 'cvlc' to use vlc without interface.
[00007fdcc8c01838] mp4 demux error: cannot find any /moov/trak
QObject::~QObject: Timers cannot be stopped from another thread

I have tried every combination of extension (.avi, .mp4) and codec (MJPG, DIVX, XVID, H264) and none of the videos are playable.

Any idea what's wrong?

python
opencv
video
vlc
codec
asked on Stack Overflow Jul 18, 2017 by lollercoaster • edited Jul 18, 2017 by lollercoaster

1 Answer

3

Following the discussion https://github.com/ContinuumIO/anaconda-issues/issues/223 . I adopted jeremy-rutman's suggestion "I was able to solve this by keeping the output video dimensions identical to the input frame dimensions."

The following code worked for me, I use int(cap.get(3)) int(cap.get(4)) for the frame sizes. (my api is also a bit different like the fourcc retrieval) and also the waitKey doesn't work for me so I just loop up to 100.

import cv2
import os

extensions = ['avi','mp4']
codecs = ['MJPG','H264', 'DIVX', 'XVID', 'X264']

for ext in extensions:
    for codec in codecs:
        savepath = "output__%s.%s" % (codec, ext)
        print savepath
        try:        
            cap = cv2.VideoCapture(0)

            # and our buffer to write frames
            fourcc = cv2.cv.CV_FOURCC(*codec)
            out = cv2.VideoWriter(savepath, fourcc, 20.0,     (int(cap.get(3)),int(cap.get(4))), 1)
            i = 0;
            while i < 100:
                i = i +1

                ret, frame = cap.read()
                if not ret:
                    continue

                text = 'testing 123'
                font = cv2.FONT_HERSHEY_SIMPLEX
                cv2.putText(frame, text, (50, 50), font, 2, (255, 255, 0), 2)

                #write our frame
                out.write(frame)

                cv2.imshow('My Frame', frame)
                ch = cv2.waitKey(1)
                if ch == 27:  # ESC
                    break

            cap.release()
            out.release()
            cv2.destroyAllWindows()

            os.system("vlc %s" % savepath)

    except Exception as e:
        print "Combo codec=%s, exte=%s failed with: %s" % (codec, ext, str(e))
answered on Stack Overflow Aug 7, 2017 by dafnahaktana

User contributions licensed under CC BY-SA 3.0