Correct Width and Height Gives Error in VideoWriter

Hello fellow open visualizers! I’m having trouble using the OpenCV video writer at the moment and can’t seem to find a solution. I’m using the package Harvesters for collecting images off an industrial camera. I can collect frames, but when writing them to disk the writer fails if I give it the correct width and height of the images. If I give them reversed, the video is written but is incorrectly displayed. Here’s the code that I’m using:

# Use Capture Images to Record from Camera
def capture_images():
    # Create filename TODO: make this an input or from setup function
    filename = 'testvid.avi'
    # Define filepath for video
    directory = r"C:\Users\jdelahanty\Documents\genie_nano_videos"
    # Define number of frames to record TODO: Make this an input/from setup
    num_frames = 30
    # Preallocate an array in memory to temporarily store frames
    # Initialize np array as zeros for number of frames, width, height, 1 color channel
    img_array = np.zeros([num_frames, width, height], dtype=np.uint8)

    os.chdir(directory)
    # Start the Camera
    h, camera = init_camera()

    # Store frames in RAM
    for i in range(num_frames):
        with camera.fetch_buffer() as buffer:
            np.copyto(img_array[i], buffer.payload.components[0].data.reshape(
            buffer.payload.components[0].width, buffer.payload.components[0].height
            ))
    # Define which video codec to use
    fourcc = cv2.VideoWriter_fourcc(*'DIVX')
    # Only writes when height and width are reversed!
    out = cv2.VideoWriter(filename, fourcc, 30, (height, width), 0)


    for i in range(len(img_array)):
        out.write(img_array[i])
    out.release()

    shutdown_camera(camera, h)

    exit(0)

The video looks like the image attached to the post. I’d show the correct image, but as a new user I can’t send multiple attachments.

It makes sense it looks the way it does since the height and width are reversed here, but using the correct positions yields an empty video file!

Any advice?

Image

It looks like I can upload a new file if it’s in a comment? Here’s what the image is supposed to look like:

Correct Image

I’m still not sure why exactly this is occurring, but I’ve found a fix for this. It’s something to do with the np.copyto() function. When reshaping the data, using buffer.payload.components[0].height as the first axis and buffer.payload.components[0].width as the second axis allows me to write videos correctly. There must be something about how np.copyto() works that doesn’t play nice with VideoWriter.

Here’s the updated code:

# Use Capture Images to Record from Camera
def capture_images():
    # Create filename TODO: make this an input or from setup function
    filename = 'testvid.avi'
    # Define filepath for video
    directory = r"C:\Users\jdelahanty\Documents\genie_nano_videos"
    # Define number of frames to record TODO: Make this an input/from setup
    num_frames = 30
    # Preallocate an array in memory to temporarily store frames
    # Initialize np array as zeros for number of frames, width, height, 1 color channel
    img_array = np.zeros([num_frames, 1024, 1280], dtype=np.uint8)

    os.chdir(directory)
    # Start the Camera
    h, camera = init_camera()
    # Store frames in RAM
    for i in range(num_frames):
        with camera.fetch_buffer() as buffer:
            np.copyto(img_array[i], buffer.payload.components[0].data.reshape(
            buffer.payload.components[0].height, buffer.payload.components[0].width
            ))
    print(img_array.shape[1], img_array.shape[2])
    plt.imshow(img_array[-1])
    plt.show()
    # Define which video codec to use
    fourcc = cv2.VideoWriter_fourcc(*'DIVX')
    # Only writes when height and width are reversed!
    out = cv2.VideoWriter(filename, fourcc, 30, (img_array.shape[2], img_array.shape[1]), 0)


    for i in range(len(img_array)):
        out.write(img_array[i])
    out.release()

    shutdown_camera(camera, h)

    sys.exit(0)

And here’s the correct display:

not the correct width and height.

the order has to be …height, width…

and that has to be (width, height)

1 Like

This is right! I’m pretty new to numpy and opencv so I didn’t know how to build the correct dimensions. Thanks crackwitz!