简体   繁体   中英

How to get the FFT image from a raw TEM tiff?

I'm trying to write code that takes TEM (Transmission Electron Microscope) TITFF images, and computes the FFT. But I always get plain Red, Green or Blue images.

Here's what the RAW TEM images look like:

原始 TEM Tiff

Here's what the FFT image should look like:

GMS软件制作的FFT

But instead I get:

代码中的 FFT

Here's my code:

import numpy as np
import diplib as dip
import matplotlib.pyplot as plt
from PIL import Image
from ncempy.io import dm


img1 = dip.ImageReadTIFF('RAW_FFT.tif')
f = np.fft.fft2(img1)
f = np.fft.fftshift(f)

plt.imshow(abs(f))
plt.show()

Do you have any idea what could be the problem? I even tried to convert the image to np.array and do FFT step by step but I get the same result.

FFT is complex and without a logarithm, Fourier transform would be so much brighter than all the other points that everything else will appear black. see for details: https://homepages.inf.ed.ac.uk/rbf/HIPR2/fourier.htm

import cv2
import numpy as np

img=cv2.imread('inputfolder/yourimage.jpg',0)
def fft_image_inv(image):
    f = np.fft.fft2(image)
    fshift = np.fft.fftshift(f)
    magnitude_spectrum = 15*np.log(np.abs(fshift))
    return magnitude_spectrum

fft= fft_image_inv(img)
cv2.imwrite('outputfolder/yourimage.jpg',fft)

output: 在此处输入图像描述

There are multiple issues here. First, sometimes grayscale images are written to file as if they were RGB images (in a TIFF file, this could be as simple as storing a grayscale color map, the pixel values will be interpreted as indices into the map, and the loaded image will be an RGB image instead of a grayscale image, even through it has only grayscale colors).

This is the case here. All three channels have exactly the same information, but there are three channels stored, and your FFT will compute the same thing three times!

After loading the image with dip.ImageReadTIFF() , you can use parentheses to index one of the channels:

img1 = dip.ImageReadTIFF('RAW_FFT.tif')
img1 = img1(0)

We now have an actual gray-scale image. This should get rid of the red color in the output.

After computing the FFT, we have a floating-point image with a very high dynamic range (the largest magnitude, at the middle pixel, is 437536704). pyplot, by default, will show floating-point images with 0 and all negative values as black, and 1 and all larger values as white (actual colors depend of course on the color map it uses). So your display will be all white. Use the vmax parameter to imshow to determine the value shown as white. Setting this to 1e6 should give you a similar display as in the GMS software.

Instead of pyplot you can use DIPlib for display. Its interactive viewer will let you use a slider to manually set the grayscale limits, and you can manually select to display the magnitude, as well as choose a logarithmic mapping (which tend to be most useful for displaying the frequency domain).

f = dip.FourierTransform(img)
dip.viewer.ShowModal(f)

Alternatively, you can use a static display, which uses pyplot under the hood:

f.Show((0, 1e6))

or

f.Show('log')

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM