I have 12, three channels, RGB pictures (.jpeg). I would like to merge them in a unique 12 channels image using python.
I tried the following code converting each picture in a numpy array. I successfully create a 3D array with 12 arrays on axes 2 but it seems that PIL does not support saving multichannel images:
from PIL import Image
import numpy as np
# Load the first image
path = 'test_img_0000_Ch1.jpeg'
img = Image.open(path)
arr = np.array(img.convert('L'))
for x in range(2, 13):
path = '_test_img_0000_Ch{x}.jpeg'
img = Image.open(path)
array_stack = np.array(img.convert('L'))
arr = np.dstack((arr, array_stack))
image = Image.fromarray(arr)
image.save("multichannel.jpeg")
You can create a "multi-page" TIFF with 12 images, each 640px wide and 480px tall like this:
from tifffile import imwrite
import numpy as np
# Create stack of 12 images, each 640x480 pixels
data = np.zeros((12,480,640), np.uint8)
# Make first image fully black, 2nd image grey(20), 3rd image grey(40)
for i in range(12):
data[i, :, :] = 20 * i
# Save as 12 image multi-page TIFF
imwrite('result.tif', data, photometric='minisblack')
If you now open it in macOS Preview image viewer, you will see the single TIFF file contains 12 images, each one successively lighter than the previous one:
And if you check its content with ImageMagick, you will find 12 individual images within the singe TIFF:
identify result.tif
result.tif[0] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 3.51761MiB 0.000u 0:00.000
result.tif[1] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
result.tif[2] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
result.tif[3] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
result.tif[4] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
result.tif[5] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
result.tif[6] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
result.tif[7] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
result.tif[8] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
result.tif[9] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
result.tif[10] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
result.tif[11] TIFF 640x480 640x480+0+0 8-bit Grayscale Gray 0.000u 0:00.000
If you now want to read it back in, and take channels 0, 6 and 11 as R, G and B:
from tifffile import imread
from PIL import Image
im = imread('result.tif')
# Take channels 0, 6 and 11 as R, G and B
rgb = np.dstack((im[0], im[6], im[11]))
Image.fromarray(rgb).save('result.jpg')
The red channel is zero, the green channel is 120 and the blue channel is 220, so the result is largely blueish.