Cerin
Cerin

Reputation: 64739

Calculating DCT with OpenCV

I'm attempting to use the dct() function in OpenCV to calculate the discrete cosine transform, but I'm getting strange results.

My script is:

import os, sys
import cv, cv2
import numpy as np

fn1 = 'original.jpg'
img1 = cv2.imread(fn1, cv2.CV_LOAD_IMAGE_GRAYSCALE)

h, w = img1.shape[:2]
vis0 = np.zeros((h,w), np.float32)
vis0[:h, :w] = img1
vis1 = cv2.dct(vis0)
img2 = cv.CreateMat(vis1.shape[0], vis1.shape[1], cv.CV_32FC3)
cv.CvtColor(cv.fromarray(vis1), img2, cv.CV_GRAY2BGR)

cv.ShowImage('',img2)
cv2.waitKey()
cv.SaveImage('saved.jpg', img2)

This appears to run without error, but the image shown by ShowImage() and the image saved by SaveImage() appear very different. Unfortunately, I can't seem to find any sample images of a DCT-processed image, so I'm not sure which, if either, is correct.

The original image: original

The shown DCT image: shown

The saved DCT image: saved

Why is there such a difference between the shown and saved DCT images? Which is correct?

Upvotes: 3

Views: 9492

Answers (2)

Peb
Peb

Reputation: 171

the saved image is actually the same but the values are clamped to [0..255] and converted to byte (numpy.uint8) before it is saved as JPEG. negative values are set to zero and values above 255 are set to 255.

cv2.imshow("before_save", vis1)
vis1[vis1>255] = 255
vis1[vis1<0] = 0
cv2.imshow("saved", vis1.astype(np.uint8))

Upvotes: 2

Sam
Sam

Reputation: 20056

It seems that you displayed the complex output of the DCT. And, because you tried to save a 2-channel image (DCT outputs 2 channels - one for real, one for imaginary part), it saved only the real part (which is somehow close to the magnitude).

So, from your DCT output, use the magnitude() and phase() functions to extract useful info. Display them separately,

And, most important, read carefully about DCT ( http://en.wikipedia.org/wiki/Discrete_cosine_transform ) so you know what you're doing.

Upvotes: 2

Related Questions