Recording more than 4 channel images in OpenCV Python

It's kind of a constant challenge for me. I am trying to combine two 3 RGB images into one 6 channel TIFF image using openCV.

So far, my code looks like this:

import cv2
import numpy as np

im1 = cv2.imread('im1.jpg')
im2 = cv2.imread('im2.jpg')

merged = np.concatenate((im1, im2), axis=2) # creates a numpy array with 6 channels 

cv2.imwrite('merged.tiff', merged)

      

I have also tried using openCV split () and merge () methods and get the same results

import cv2
import numpy as np

im1 = cv2.imread('im1.jpg')
im2 = cv2.imread('im2.jpg')

b1,g1,r1 = cv2.split(im1)
b2,g2,r2 = cv2.split(im2)

merged = cv2.merge((b1,g1,r1,b2,g2,r2))

cv2.imwrite('merged.tiff', merged)

      

When I run the imwrite () function, I get the following error:

OpenCV Error: Assertion failed (image.channels () == 1 || image.channels () == 3 || image.channels () == 4) in cv :: imwrite_, file C: \ builds \ master_PackSlaveAddon-win32 -vc12-static \ opencv \ modules \ imgcodecs \ src \ loadsave.cpp, line 455
Traceback (most recent call last):
  File "", line 1, in 
cv2.error: C: \ builds \ master_PackSlaveAddon-win32-vc12-static \ opencv \ modules \ imgcodecs \ src \ loadsave.cpp: 455: error: (-215) image.channels () == 1 || image.channels () == 3 || image.channels () == 4 in function cv :: imwrite_

Both images are identical in size (900X1200). I think openCV cannot write more than 4 channels (RGBA) to a tiff image and I had no luck finding an alternative way to encode this image.

I am flirting with the idea of ​​making my own function to write binary data with appropriate headers, but this is much deeper than I want.

Is there another function in openCV that I can use that will work, or another library that can write this numpy array to a tiff with 6 channels?

+3


source to share


1 answer


OpenCV uses internally libpng

, libtiff

etc. modules for recording RGB images. As various image formats such as jpg

, png

etc., assume that the input array should be a single channel, 3 channels or 4 channels. The assumption is made to optimize the disk size on disk. But the same assumption would be violated in a 6-channel matrix.

So you can use a serialization library such as pickle

, it can be used in general to serialize any Python object, in which case you want to serialize a numpy matrix, so it will work fine, however you won't be able to take advantage of the compression methods used in the format png

or jpg

.



import numpy as np
import pickle

arr = np.ones((1000, 1000, 6), dtype=np.uint8) * 255

with open("arr_dump.pickle", "wb") as f_out:
    pickle.dump(arr, f_out)

with open("arr_dump.pickle", "rb") as f_in:
    arr_new = pickle.load(f_in)
    print arr_new.shape

      

However, if you are concerned about file size and want to use memory optimizations tiff

or png

etc, then I would recommend that you split your 6 channel image into different channels and create 2 new 3 channel matrices and use imwrite to save and read them. read both images and combine them with a 6-channel image.

+1


source







All Articles