def jpegCompress(image, quantmatrix): ''' Compress(imagefile, quanmatrix simulates the lossy compression of baseline JPEG, by quantizing the DCT coefficients in 8x8 blocks ''' # Return compressed image in result H = np.size(image, 0) W = np.size(image, 1) # Convert to gray-scale image if np.size(image, 2) > 1: image = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY) # Number of 8x8 blocks in the height and width directions h8 = H / 8 w8 = W / 8 iH = H iW = W # Padding image if H % 8 != 0: image = np.lib.pad(image, ((0, 8 - H % 8), (0, 0)), 'constant', constant_values=((0, 0), (0, 0))) h8 += 1 if W % 8 != 0: image = np.lib.pad(image, ((0, 0), (0, 8 - W % 8)), 'constant', constant_values=((0, 0), (0, 0))) w8 += 1 image = image.astype("float") dct_coefficient = image.copy() result = image.copy() # Calculate DCT coefficients for patches for i in xrange(h8): for j in xrange(w8): h_start, h_end, w_start, w_end = patchRegion(i, j) patch = image[h_start : h_end, w_start : w_end] cv2.dct(patch, patch) # Quantization patch = np.round(patch / quantmatrix) dct_coefficient[h_start : h_end, w_start : w_end] = patch # Convert back for i in xrange(h8): for j in xrange(w8): h_start, h_end, w_start, w_end = patchRegion(i, j) patch = dct_coefficient[h_start : h_end, w_start : w_end] cv2.idct(patch, patch) result[h_start : h_end, w_start : w_end] = patch # Remove padding effect result = result[0 : iH, 0 : iW] return result
def dct(img): """Computes discrete cosine transform of an image""" global SIZE imf = np.float32(img)/255.0 # float conversion/scale dst = cv2.dct(imf) # the dct img = np.uint8(dst)*255.0 # convert back img = img[0:SIZE,0:SIZE] return img
def get_sdct(array): """ Secure discrete cosine trasform <octave way> """ try: return cv2.dct(array) except: return cv2.dct(array[:-1, :-1])
def classify_pHash(image1, image2): image1 = cv2.resize(image1, (32, 32)) image2 = cv2.resize(image2, (32, 32)) gray1 = cv2.cvtColor(image1, cv2.COLOR_BGR2GRAY) gray2 = cv2.cvtColor(image2, cv2.COLOR_BGR2GRAY)# 将灰度图转为浮点型, 再进行dct变换 dct1 = cv2.dct(np.float32(gray1)) dct2 = cv2.dct(np.float32(gray2))# 取左上角的8 * 8, 这些代表图片的最低频率# 这个操作等价于c++中利用opencv实现的掩码操作# 在python中进行掩码操作, 可以直接这样取出图像矩阵的某一部分 dct1_roi = dct1[0: 8, 0: 8] dct2_roi = dct2[0: 8, 0: 8] hash1 = getHash(dct1_roi) hash2 = getHash(dct2_roi) return Hamming_distance(hash1, hash2)
def jpegCompress(image, quantmatrix): ''' Compress(imagefile, quanmatrix simulates the lossy compression of baseline JPEG, by quantizing the DCT coefficients in 8x8 blocks ''' # Return compressed image in result H = np.size(image, 0) W = np.size(image, 1) # Number of 8x8 blocks in the height and width directions h8, w8 = np.ceil((H / 8, W / 8)).astype('int') # TODO If not an integer number of blocks, pad it with zeros result = np.pad(image.astype('float'), ((0, h8 * 8 - H), (0, w8 * 8 - W), (0, 0)), 'constant', constant_values=(0, 0)) # TODO Separate the result into blocks, and compress the blocks via # quantization DCT coefficients for i in range(0, h8 * 8, 8): for j in range(0, w8 * 8, 8): mat = np.round(np.divide(cv2.dct(result[i:i + 8, j:j + 8, 0] - 128), quantmatrix)) result[i:i+8, j:j+8, :] = np.reshape(mat,(8,8,1)) # TODO Convert back from DCT domain to RGB result for i in range(0, h8 * 8, 8): for j in range(0, w8 * 8, 8): mat = cv2.idct(np.multiply(result[i:i + 8, j:j + 8, 0], quantmatrix)) + 128 result[i:i+8, j:j+8, :] = np.reshape(mat,(8,8,1)) return result[:H, :W, :].astype('uint8')
def _customDCT_(block): """applying DCT in a macroblock""" imf = np.float32(block) / 255.0 # float conversion/scale dst = cv2.dct(imf) # the dct img = np.uint8(dst) * 255.0 return img
def dctImage(subjectNo, imgNo): imgAddress = 'D:\Final Year Project\Code\RealWorldDatabase\Conditioned\s'+str(subjectNo)+'\\'+str(imgNo)+'.jpg' img1 = cv2.imread(imgAddress, 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) # DCT coefficients #img2 = cv.CreateMat(vis1.shape[0], vis1.shape[1], cv.CV_32FC3) #cv.CvtColor(cv.fromarray(vis1), img2, cv.CV_GRAY2BGR) #cv.SaveImage('C:\Users\Rahul Nafde\Desktop\output1.jpg', img2) #print vis1; #print h,'x',w fileAddress = 'D:\Final Year Project\Code\DCTcoefficients' fileName = fileAddress+'\s'+str(subjectNo)+'\\'+str(imgNo)+'.txt' #fo = open(fileName,"w+") #fo.write("###\n") np.savetxt(fileName,vis1,fmt='%7.7e') #fo.close() return
def dct2_nxn(i): out = np.empty_like(i) for x in range(out.shape[1]): for y in range(out.shape[0]): # out[y, x] = dct(dct(i[y, x], axis=1, norm='ortho'), axis=0, norm='ortho') out[y, x] = cv2.dct(i[y, x]) return out
def _calculate( self ): img = self._img.grayscale().resize( (32, 32), cv2.INTER_NEAREST ) imf = np.float32( img._img ) / 255.0 dsty = cv2.dct( imf )[0:8] dst = [] for i in xrange( len( dsty ) ): dst.append( dsty[i][0:8] ) c = a = 0 for j in xrange( len( dst ) ): y = dst[j] for i in xrange( len( y ) ): if i == 0 and j == 0: continue c += 1 a += y[i] median = a / c result = int64() for row in xrange( 8 ): for col in xrange( 8 ): result <<= 1 result |= 1 * ( dst[col][row] > median ) return result
def process(self,img): img = img.astype(float) #img.dtype = np.float extra = {} if self.flags.value!=None: extra['flags'] = self.flags.value img = cv2.dct(img,**extra) #img.dtype = np.uint8 return img
def get_w(m): s = m.shape w = cv.dct(m) w *= 2.0 / sqrt(s[0] * s[1]) #w[0,0] *= 0.5 w[:, 0] *= sqrt(0.5) w[0, :] *= sqrt(0.5) w = w[0:basis_size[0], 0:basis_size[1]].transpose().flatten() return w
def lisanyuxian(): img1 = cv2.imread(name, 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)
def dctC(img, size, mask): # Do 8x8 DCT on image i = 0 DCT = np.zeros((size[0], size[1]), np.float32) while i < size[0]: j = 0 while j < size[1]: DCT[i:i+8, j:j+8] = cv2.dct(np.float32(img[i:i+8, j:j+8])) * mask j += 8 i += 8 return DCT
def get_dct(filename='0.jpg'): img = cv2.imread(os.path.join('images', filename), cv2.CV_LOAD_IMAGE_GRAYSCALE) h, w = img.shape ret = numpy.ndarray(h * w / 64, dtype=numpy.dtype((numpy.float32, (8, 8)))) mat = numpy.zeros((8, 8), numpy.float32) for r, c in block_coordinates: mat[:8, :8] = img[r:r + 8, c:c + 8] dct = cv2.dct(mat) ret[r + c / 8][:, :] = dct return ret
def discrete_cosine_transform(divided_mtrx): rows = len(divided_mtrx) columns = len(divided_mtrx[0]) dct_mtrx = [ [ [[]] for i in range(rows) ] for j in range(columns) ] for i in range(0, rows): for j in range(0, columns): imf = np.float32(divided_mtrx[i][j])/255.0 dst = cv2.dct(imf) dct_mtrx[i][j] = dst return dct_mtrx
def regul_filtInv_dct(img_bruitee,filtre,name=""): """ Methode de filtrage inverse régularisée par la cdt """ plt.figure() plt.title("Filtrage inverse sur {}".format(name)) t_img = cv2.dct(img_bruitee) t = mDCT(np.fft.fft2(filtre)) for alpha in np.logspace(-6,2,9): divF = np.divide(np.multiply(t_img,t),np.add(np.power(t,2),alpha)) invF = cv2.idct(divF) plt.figure() plt.suptitle("Dct regul avec alpha = {}".format(alpha)) plt.imshow(abs(invF),cmap='gray')
def lisanyuxian(): '''离散余弦变换函数 调用opencv库函数,进行离散余弦变换''' img1 = cv2.imread(filepath,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) print(img2) cv.ShowImage('离散余弦变换',img2) cv.WaitKey(0)
def hash(self, path): gray = cv2.imread(path, 0) if gray is None: return None gray = cv2.blur(gray, (7,7)) gray = cv2.resize(gray, (32,32)) gray = cv2.dct(np.asarray(gray, np.float)) vec = gray[1:9, 1:9].flatten() median = np.median(vec) hash_val = 0 for v in vec: if v > median: hash_val |= 1 hash_val = hash_val << 1 return hash_val
def p_hash(image): """ 感知哈希算法(pHash) 均值哈希虽然简单,但是受均值影响大。如果对图像进行伽马校正或者进行直方图均值化都会影响均值,从而影响哈希值的计算。所以就有人提出更健壮的方法,通过离散余弦(DCT)进行低频提取。 离散余弦变换(DCT)是种图像压缩算法,它将图像从像素域变换到频率域。然后一般图像都存在很多冗余和相关性的,所以转换到频率域之后,只有很少的一部分频率分量的系数才不为0,大部分系数都为0(或者说接近于0)。Phash哈希算法过于严格,不够精确,更适合搜索缩略图,为了获得更精确的结果可以选择感知哈希算法,它采用的是DCT(离散余弦变换)来降低频率的方法。 pHash的hanming距离步骤: 1. 缩小图片:32 * 32是一个较好的大小,这样方便DCT计算转化为灰度图 2. 计算DCT:利用Opencv中提供的dct()方法,注意输入的图像必须是32位浮点型,所以先利用numpy中的float32进行转换 3. 缩小DCT:DCT计算后的矩阵是32 * 32,保留左上角的8 * 8,这些代表的图片的最低频率 4. 计算平均值:计算缩小DCT后的所有像素点的平均值。 5. 进一步减小DCT:大于平均值记录为1,反之记录为0. 6. 得到信息指纹:组合64个信息位,顺序随意保持一致性。 7. 最后比对两张图片的指纹,获得汉明距离即可。 :param image: :return: """ # 加载并调整图片为32*32的灰度图片 resize_image = cv2.resize(image, (32, 32), cv2.COLOR_RGB2GRAY) # 创建二维列表 h, w = image.shape[:2] vis0 = np.zeros((h, w), np.float32) vis0[:h, :w] = resize_image # DCT二维变换 # 离散余弦变换,得到dct系数矩阵 img_dct = cv2.dct(cv2.dct(vis0)) img_dct.resize(8, 8) # 把list变成一维list img_list = np.array().flatten(img_dct.tolist()) # 计算均值 img_mean = cv2.mean(img_list) avg_list = ['0' if i < img_mean else '1' for i in img_list] result = ''.join( ['%x' % int(''.join(avg_list[x:x + 4]), 2) for x in range(0, 64, 4)]) log.info('The image p_hash is: {}'.format(result)) return result
def insert_mark(self): """插入水印""" if self.filename.get() == '': # 获取图片名称 tkMessageBox.showwarning(message='输入不能为空') else: self.image = cv2.resize(self.image, (self.size, self.size)) D = self.image.copy() # 复制原图片 # DCT变换代码 alfa = 10 for p in range(self.size / self.K): for q in range(self.size / self.K): x = p * self.K y = q * self.K img_B = np.float32(D[x:x + self.K, y:y + self.K, 0]) I_dct1 = cv2.dct(img_B) if self.mark[p, q, 0] < 100: Key = self.Key1 else: Key = self.Key2 I_dct_A = I_dct1.copy() I_dct_A[0, 7] = I_dct1[0, 7] + alfa * Key[0] I_dct_A[1, 6] = I_dct1[1, 6] + alfa * Key[1] I_dct_A[2, 5] = I_dct1[2, 5] + alfa * Key[2] I_dct_A[3, 4] = I_dct1[3, 4] + alfa * Key[3] I_dct_A[4, 3] = I_dct1[4, 3] + alfa * Key[4] I_dct_A[5, 2] = I_dct1[5, 2] + alfa * Key[5] I_dct_A[6, 1] = I_dct1[6, 1] + alfa * Key[6] I_dct_A[7, 0] = I_dct1[7, 0] + alfa * Key[7] I_dct_A = np.array(I_dct_A) I_dct_a = cv2.idct(I_dct_A) max_point = np.max(I_dct_a) min_point = np.min(I_dct_a) D[x:x + self.K, y:y + self.K, 0] = I_dct_a self.picture = D E = D.copy() filename = self.filename.get() cv2.imwrite(filename, E) E = self.change_channals(E) E = np.uint8(E) cv2.imwrite(filename, E) self.pic_with_watermark.imshow(E) self.canvas.draw()
def ImageExtract(embeded_image_path, output_path): img = cv2.imread(embeded_image_path, cv2.IMREAD_GRAYSCALE) iHeight, iWidth = img.shape index = 0 length_string = "" watermark_length = 0 watermark_string = "" decoded_watermark = "" # 分块DCT for startY in range(0, iHeight, 8): for startX in range(0, iWidth, 8): block = img[startY:startY + 8, startX:startX + 8].reshape((8, 8)) # 进行DCT,并提取水印 blockf = np.float32(block) block_dct = cv2.dct(blockf) if index < 8 * 7: # 提取水印长度 bit = extract_bit(block_dct) if bit == 1: length_string += "1" else: length_string += "0" if index == 8 * 7 - 1: length_string = get_original_bin(length_string, 7) watermark_length = int(length_string, 2) index += 1 elif index < 8 * 7 + watermark_length * 8 * 7: # 提取水印 bit = extract_bit(block_dct) if bit == 1: watermark_string += "1" else: watermark_string += "0" if index == 8 * 7 + watermark_length * 8 * 7 - 1: watermark_string = get_original_bin(watermark_string, 7) # print(watermark_string) for i in range(watermark_length): decoded_watermark += chr( int(watermark_string[i * 8:(i + 1) * 8], 2)) print("提取水印:", decoded_watermark.encode()) index += 1 water_outfile = open(output_path, 'w') # 提取内容部分gbk无法编码 water_outfile.write(str(decoded_watermark.encode('utf-8'))) # write() 只能写入字符串str类型 # .encode('utf-8') 'ascii' 'CP437' 'gbk' water_outfile.close() return None
def extract_watermark(embeded_image_path): image = cv2.imread(embeded_image_path, cv2.IMREAD_COLOR) image = cv2.cvtColor(image, cv2.COLOR_BGR2YCR_CB) img = image[:, :, 0] iHeight, iWidth = img.shape countHeight = int(iHeight / 8) countWidth = int(iWidth / 8) index = 0 length_string = "" watermark_length = 0 watermark_string = "" # 分块DCT for startY in range(0, countHeight * 8, 8): for startX in range(0, countWidth * 8, 8): block = img[startY:startY + 8, startX:startX + 8].reshape((8, 8)) # 进行DCT blockf = np.float32(block) block_dct = cv2.dct(blockf) if index < 8 * SPREAD_WIDTH: bit = extract_bit(block_dct) if bit == 1: length_string += "1" else: length_string += "0" if index == 8 * SPREAD_WIDTH - 1: length_string = get_original_bin(length_string, SPREAD_WIDTH) watermark_length = int(length_string, 2) index += 1 elif index < 8 * SPREAD_WIDTH + watermark_length * 8 * SPREAD_WIDTH: bit = extract_bit(block_dct) if bit == 1: watermark_string += "1" else: watermark_string += "0" if index == 8 * SPREAD_WIDTH + watermark_length * 8 * SPREAD_WIDTH - 1: watermark_string = get_original_bin( watermark_string, SPREAD_WIDTH) decoded_watermark = "" for i in range(watermark_length): decoded_watermark += chr( int(watermark_string[i * 8:(i + 1) * 8], 2)) print(decoded_watermark) return decoded_watermark index += 1
def breakImageIntoBlocks(data, lenghtMessage): blocks = [] blocks = np.reshape(data, (lenghtMessage, 8, 8)) blocks = np.float32(blocks) blockDCT = [] for i in range(0, lenghtMessage): blockDCT.append(cv2.dct(blocks[i])) blockDCT = np.asarray(blockDCT) blocksQuantized = [] for i in range(0, lenghtMessage): blocksQuantized.append(np.divide(blockDCT[i], QUANTIZATION_TABLE)) blocksQuantized = np.asarray(blocksQuantized) return blocksQuantized
def gray_image_dct(image: np.ndarray, dct_h: int = 8, dct_w: int = 8) -> np.ndarray: """ 灰度图片的离散余弦变换 :param image: :param dct_h: :param dct_w: :return: """ h, w = np.shape(image) float_image = np.zeros_like(image, np.float32) float_image[:h, :w] = image dct_transformer = cv2.dct(float_image)[:dct_h, :dct_w].flatten() return dct_transformer
def image_dct(self, channel_index): vis0 = np.zeros((self.image_height, self.image_width), np.float64) Trans = np.zeros((self.image_height, self.image_width), np.float64) vis0[:self.image_height, :self.image_width] = self.get_channel_matrix( channel_index=channel_index) for row in range(self.blocks_vertical): for col in range(self.blocks_horizontal): current_block = cv2.dct(vis0[row * self.B:(row + 1) * self.B, col * self.B:(col + 1) * self.B]) self.dct_blocks.append(current_block) Trans[row * self.B:(row + 1) * self.B, col * self.B:(col + 1) * self.B] = current_block return
def p_hash(img, shape=True): '''shape参数用于比较两张图片, 默认为True''' # 加载并调整图片为高x宽灰度图片 img = cv2.imread(img, cv2.IMREAD_GRAYSCALE) h, w = (48, int(48 * img.shape[1] / img.shape[0])) if shape else (48, 48) # 三个参数分别为源,图片的x&y(也就是宽&高), 缩小处理方法 img = cv2.resize(img, (w, h), interpolation=cv2.INTER_CUBIC) # 创建二维列表 vis0 = np.zeros((h, w), np.float32) vis0[:h, :w] = img # 二维Dct变换 vis1 = cv2.dct(cv2.dct(vis0)) # 利用离散余弦变换,截取左上角高能指纹区 if w > h: # 高宽比, 保持较窄的为8 vis1.resize(8, int(8 * w / h)) else: vis1.resize(int(8 * h / w), 8) # 把二维list变成一维list img_list = flatten(vis1.tolist()) # 计算均值 avg = sum(img_list) / len(img_list) avg_list = ['0' if i < avg else '1' for i in img_list] # 得到16进制哈希值 print(''.join([ '%x' % int(''.join(avg_list[x:x + 4]), 2) for x in range(0, len(avg_list), 4) ])) return avg_list
def dct(img): img_data = img.astype(float) m, n = img_data.shape img_dct = np.zeros(img.shape) x_batchsize = int(m/8) y_batchsize = int(n/8) for i in range(0,x_batchsize): for j in range(0,y_batchsize): window_x_s = i * 8 window_x = (i+1) * 8 window_y_s = j * 8 window_y = (j+1) * 8 img_dct[window_x_s:window_x, window_y_s:window_y] = cv2.dct(img_data[window_x_s:window_x,window_y_s:window_y]) / quantization return img_dct
def classify_pHash(image1, image2, size=(32, 32)): """ 灰度图转为浮点型,进行平均哈希算法计算 :param image1:用于对比的图片1 :param image2:用于对比的图片2 :param size:请求的大小(以像素为单位) :return:相似度 """ image1 = cv2.resize(image1, size) image2 = cv2.resize(image2, size) gray1 = cv2.cvtColor(image1, cv2.COLOR_BGR2GRAY) gray2 = cv2.cvtColor(image2, cv2.COLOR_BGR2GRAY) # 将灰度图转为浮点型,再进行dct变换 dct1 = cv2.dct(np.float32(gray1)) dct2 = cv2.dct(np.float32(gray2)) # 取左上角的8*8,这些代表图片的最低频率 # 这个操作等价于c++中利用opencv实现的掩码操作 # 在python中进行掩码操作,可以直接这样取出图像矩阵的某一部分 dct1_roi = dct1[0:size[0], 0:size[1]] dct2_roi = dct2[0:size[0], 0:size[1]] hash1 = getHash(dct1_roi) hash2 = getHash(dct2_roi) return 1 - hamming_distance(hash1, hash2) / (size[0] * size[1])
def phash(img): #加载并调整图片为32x32灰度图片 img = cv2.resize(img, (8, 8), interpolation=cv2.INTER_CUBIC) img = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) img = img.astype(np.float32) #离散余弦变换 img = cv2.dct(img) hash_str = '' img = img[0:8, 0:8] avg = sum(img[i, j] for i, j in itertools.product(range(8), range(8))) avg = avg / 64 #获得hsah for i, j in itertools.product(range(8), range(8)): hash_str = f'{hash_str}1' if img[i, j] > avg else f'{hash_str}0' return hash_str
def pHash(img): img = cv2.resize(img, (32, 32)) #interpolation=cv2.INTER_CUBIC gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) # 转换为灰度图 dct = cv2.dct(np.float32(gray)) # 将灰度图转为浮点型,再进行dct变换 dct_roi = dct[0:8, 0:8] #opencv实现的掩码操作 hash = [] avreage = np.mean(dct_roi) for i in range(dct_roi.shape[0]): for j in range(dct_roi.shape[1]): if dct_roi[i, j] > avreage: hash.append(1) else: hash.append(0) #print("hash:"+str(hash)) return hash
def get_image_features(image): bins = 8 image = cv2.resize(image, (200, 200)) hsv_image = cv2.cvtColor(image, cv2.COLOR_BGR2HSV) hist = cv2.calcHist([hsv_image], [0, 1, 2], None, [bins, bins, bins], [0, 256, 0, 256, 0, 256]) # flating cv2.normalize(hist, hist) features = hist.flatten() gray_image = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY) std_image = np.float32(gray_image) / 255.0 dct = cv2.dct(std_image) features = np.concatenate((features, dct), axis=None) return features
def classify_pHash(self, img1): gray1 = cv2.cvtColor(np.asarray(img1), cv2.COLOR_BGR2GRAY) gray1 = cv2.resize(gray1, (32, 32)) # 将灰度图转为浮点型,再进行dct变换 dct1 = cv2.dct(np.float32(gray1)) # 取左上角的8*8,这些代表图片的最低频率 # 这个操作等价于c++中利用opencv实现的掩码操作 # 在python中进行掩码操作,可以直接这样取出图像矩阵的某一部分 dct1_roi = dct1[0:8, 0:8] hash1 = self.getHash(dct1_roi) # print(hash1) # decimal_value = 0 hash1 = self.magic(hash1) hash1 = hex(int(hash1, 2)) return hash1.rstrip()
def transform(block,k,iden): # print(block) block=block-128 block_dct=cv2.dct(block/255.0)*255 # print(block_dct.astype(int)) if iden==0: block_dct=block_dct/(ll*k) if iden==1: block_dct=block_dct/(lc*k) # print(block_dct) return block_dct
def DCT_of_each_subblock(img_subblock): normalized_img = np.float32(img_subblock) / 255.0 rows, cols, total_blocks = img_subblock.shape[0], img_subblock.shape[ 1], img_subblock.shape[2] img_dct = np.zeros((rows, cols, total_blocks), dtype='float32') for i in range(total_blocks): img_dct[:, :, i] = cv2.dct(normalized_img[:, :, i]) img_dct = img_dct * 255 img_dct = img_dct.astype(dtype='int32') return img_dct
def encoder(): block_size = 8 img = data.chelsea() img = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) #cv2.imshow('input image', img) #cv2.waitKey(0) # get size of the image [h, w] = img.shape # compute number of blocks by diving height and width of image by block size h = np.float32(h) w = np.float32(w) nbh = math.ceil(h / block_size) nbh = np.int32(nbh) nbw = math.ceil(w / block_size) nbw = np.int32(nbw) H = block_size * nbh W = block_size * nbw padded_img = np.zeros((H, W)) for i in range(h): for j in range(w): pixel = img[i, j] padded_img[i, j] = pixel #cv2.imshow('input padded image', np.uint8(padded_img)) for i in range(nbh): row_ind_1 = i * block_size # Compute end row index of the block row_ind_2 = row_ind_1 + block_size for j in range(nbw): col_ind_1 = j * block_size col_ind_2 = col_ind_1 + block_size block = padded_img[row_ind_1:row_ind_2, col_ind_1:col_ind_2] DCT = cv2.dct(block) reordered = zigzag(DCT) reshaped = np.reshape(reordered, (block_size, block_size)) padded_img[row_ind_1:row_ind_2, col_ind_1:col_ind_2] = reshaped #cv2.imshow('encoded image', np.uint8(padded_img)) np.savetxt('./encoded.txt', padded_img) np.savetxt('./size.txt', [h, w, block_size]) plt.subplot(211), plt.imshow(img, cmap='gray') plt.title('origin') plt.subplot(212), plt.imshow(padded_img, cmap='gray') plt.title('after padded') plt.show()
def ImageEmbed(image_path, watermark_str, output_path): rgb_image = cv2.imread(image_path, cv2.IMREAD_COLOR) ycbcr_image = cv2.cvtColor(rgb_image, cv2.COLOR_BGR2YCR_CB) img = ycbcr_image[:, :, 0] print("原始水印:", watermark_str) watermark = watermark_encode(watermark_str) iHeight, iWidth = img.shape # 初始化空矩阵保存量化结果 img2 = np.empty(shape=(iHeight, iWidth)) index = 0 alpha = 25 # 分块DCT for startY in range(0, iHeight, 8): for startX in range(0, iWidth, 8): block = img[startY:startY + 8, startX:startX + 8].reshape((8, 8)) # 进行DCT,并嵌入水印 blockf = np.float32(block) block_dct = cv2.dct(blockf) if index < len(watermark): embed_bit(int(watermark[index]), block_dct, alpha) index += 1 # store the result for y in range(8): for x in range(8): img2[startY + y, startX + x] = block_dct[y, x] # DCT逆变换 for startY in range(0, iHeight, 8): for startX in range(0, iWidth, 8): block = img2[startY:startY + 8, startX:startX + 8].reshape((8, 8)) blockf = np.float32(block) dst = cv2.idct(blockf) # 保存逆变换结果 for y in range(8): for x in range(8): img[startY + y, startX + x] = dst[y, x] # 将Y分量覆盖原来的Y分量,CbCr分量保持不变 new_ycbcr_image = ycbcr_image new_ycbcr_image[:, :, 0] = img # 将嵌入水印后的图像二维数组转化为BGR色彩空间,并写入图像 watermarked_rgb = cv2.cvtColor(new_ycbcr_image, cv2.COLOR_YCR_CB2BGR) cv2.imwrite(output_path, watermarked_rgb) return None
def raaft(patch, which_norm, inner=0, outer=1): """ Given an image patch and choice of norm, generate the RAAFT feature vector for that patch. Parameters ---------- patch : 2D numpy array The patch which we want to apply the RAAFT to. which_norm : float Which norm to normalize the feature vector by. Can choose any real number for this value, but choosing 1 <= which_norm <= infty is the most natural. Choosing either 1 or 2 works well in most cases. inner, outer : float To help with noise it is sometimes useful to set parts of the Fourier transform of in each patch to zero. If a patch has dimensions (px, py) then the points (kx,ky) in k-space which are not set to zero must satisfy: inner * sqrt(px^2 + py^2) <= sqrt(kx^2 + ky^2) outer * sqrt(px^2 + py^2) >= sqrt(kx^2 + ky^2) Returns ------- feat_vector : 2D numpy array with shape (patch.shape[0], 1) The RAAFT feature vector corresponding to the given patch. """ p_sz = patch.shape center = (p_sz[0] // 2, p_sz[1] // 2) rad = np.sqrt((p_sz[0]**2 + p_sz[1]**2) / 2) tol = 1e-10 # this so we don't accidentally divide by 0 # #patch = (patch - np.mean(patch)) / np.std(patch) # Take the absolute value of the Fourier transform tmp_img = np.abs(fftpack.fftshift(cv2.dct(patch))) # Normalize the patch tmp_img /= norm(np.ndarray.flatten(tmp_img), ord=which_norm) + tol # Perform the polar transform tmp_img = cv2.warpPolar(tmp_img, None, center, rad, cv2.WARP_FILL_OUTLIERS + cv2.INTER_CUBIC) # Sum over the radial variable feat_vec = np.sum(tmp_img, 0) feat_vec[:int(rad * inner)] = 0 feat_vec[int(rad * outer):] = 0 return np.array(feat_vec, ndmin=2)
def DCTnQuantize(prop): #To take the DCT of the image img = prop.image iHeight, iWidth = img.shape[:2] print "size:", iWidth, "x", iHeight # set size to multiply of 8 if (iWidth % 8) != 0: filler = img[:,iWidth-1:,:] #print "width filler size", filler.shape for i in range(8 - (iWidth % 8)): img = np.append(img, filler, 1) if (iHeight % 8) != 0: filler = img[iHeight-1:,:,:] #print "height filler size", filler.shape for i in range(8 - (iHeight % 8)): img = np.append(img, filler, 0) iHeight, iWidth = img.shape[:2] print "new size:", iWidth, "x", iHeight # convert to YCrCb, Y=luminance, Cr/Cb=red/blue-difference chrominance img = cv2.cvtColor(img, cv2.COLOR_BGR2YCR_CB) # array as storage for DCT + quant.result img2 = np.empty(shape=(iHeight, iWidth, 3)) # FORWARD ---------------- # do calc. for each 8x8 non-overlapping blocks for startY in range(0, iHeight, 8): for startX in range(0, iWidth, 8): for c in range(0, 3): block = img[startY:startY+8, startX:startX+8, c:c+1].reshape(8,8) # apply DCT for a block blockf = np.float32(block) # float conversion dst = cv2.dct(blockf) # dct # quantization of the DCT coefficients blockq = np.around(np.divide(dst, quant_matrix[c])) blockq = np.multiply(blockq, quant_matrix[c]) # store the result for y in range(8): for x in range(8): img2[startY+y, startX+x, c] = blockq[y, x] prop.image = img2
def compress(image, layers, inp): for k in range(0, layers): if layers > 1: img = image[:, :, k] else: img = image sliced = [] # new list for 8x8 sliced image height = len(img) # one column of image width = len(img[0]) # one row of image # dividing block x block parts currentY = 0 # current Y index for i in range(block, height + 1, block): currentX = 0 # current X index for j in range(block, width + 1, block): sliced.append( img[currentY:i, currentX:j] ) # Extracting 128 from all pixels currentX = j currentY = i sliced = [np.float64(img) for img in sliced] # DCT on block x block parts DCToutput = [] for part in sliced: part -= np.ones((8, 8)) * 128 currentDCT = cv2.dct(part) # Quantization currentDCT = np.around(np.divide(currentDCT, Quantization)) DCToutput.append(currentDCT) # Quantization # for dct in DCToutput: # for i in range(block): # for j in range(block): # dct[i, j] = np.around(dct[i, j] / Quantization[i, j]) row = 0 rowNcol = [] DCToutput = [np.int64(part) for part in DCToutput] for j in range(width // block, len(DCToutput) + 1, width // block): rowNcol.append(np.hstack((DCToutput[row:j]))) row = j result = np.vstack((rowNcol)) result += 128 result = np.uint8(result) if layers > 1: image[:, :, k] = result else: image = result name = re.findall("(.*)[.]", inp)[0] + "Compressed" + re.findall("[.].*", inp)[0] io.imsave(name, image)
def convert_to_dct(self, image_fp, skip_status_bar_fraction=1.0): dct_obj = None try: img_obj = cv2.imread(image_fp) height, width, channel = img_obj.shape height = int(height * skip_status_bar_fraction) - int(height * skip_status_bar_fraction) % 2 img_obj = img_obj[:height][:][:] img_gray = np.zeros((height, width)) for each_channel in range(channel): img_gray += img_obj[:, :, each_channel] img_gray /= channel img_dct = img_gray / 255.0 dct_obj = cv2.dct(img_dct) except Exception as e: logger.error(e) return dct_obj
def cvdct(img): img = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) rows, cols = img.shape[:2] nrows = cv2.getOptimalDFTSize(rows) ncols = cv2.getOptimalDFTSize(cols) padded = cv2.copyMakeBorder(img, 0, nrows - rows, 0, ncols - cols, cv2.BORDER_CONSTANT, value=[0, 0, 0]) imf = np.float32(padded) dst = cv2.dct(imf) return np.uint8(dst) * 255.0
def computeDCTransform(imgPath, noOfFeatures=1024): srcImg = cv2.imread(str(imgPath)) srcImg = cv2.cvtColor(srcImg, cv2.COLOR_BGR2GRAY) #Compute DCT transform srcImg = np.array(srcImg, dtype=np.float32) dctFeats = cv2.dct(srcImg) #Thank's to https://stackoverflow.com/questions/50445847/how-to-zigzag-order-and-concatenate-the-value-every-line-using-python zigzagPattern = np.concatenate([ np.diagonal(dctFeats[::-1, :], i)[::(2 * (i % 2) - 1)] for i in range(1 - dctFeats.shape[0], dctFeats.shape[0]) ]) zigzagPattern = zigzagPattern[0:noOfFeatures] #plt.bar([i for i in range(len(zigzagPattern))], zigzagPattern) #plt.plot(dctFeats, '*r') #plt.show() return zigzagPattern
def get_DCT_pix(raster, padd, coeff_num): total = [] rastert = np.zeros((raster.shape[0], raster.shape[1], coeff_num**2), dtype=raster.dtype) print rastert.shape raster = np.lib.pad(raster, ((padd / 2, padd / 2), (padd / 2, padd / 2)), 'edge') for i in range(rastert.shape[0]): for j in range(rastert.shape[1]): coeffs = cv2.dct(raster[i:i + padd, j:j + padd]) count = 0 for c1 in range(0, coeff_num): for c2 in range(0, coeff_num): rastert[i, j, count] = coeffs[c1, c2] count += 1 return rastert
def pHash(img, leng=32, wid=32): """ 感知哈希算法 """ img = pre_handle_img(img, leng, wid) # DCT变换 dct = cv2.dct(np.float32(img)) # 掩码 dct_roi = dct[0:8, 0:8] avreage = np.mean(dct_roi) phash_01 = (dct_roi > avreage) + 0 # 行列转换,取第一列,转数组 phash_list = phash_01.reshape(1, -1)[0].tolist() hashStr = ''.join([str(x) for x in phash_list]) return hashStr
def edge_measure_dct(img, gamma): # print(img, "\n\n") img = img.astype(np.float32) roi_dct = cv.dct(img) # print(roi_dct, "\n") theta0 = abs(roi_dct[1, 0]) / 4 theta90 = abs(roi_dct[0, 1]) / 4 theta45 = 1 / 6 * max(abs(roi_dct[1, 0] + roi_dct[0, 1] + roi_dct[1, 1]), abs(roi_dct[1, 1] - roi_dct[0, 1] - roi_dct[1, 0])) theta135 = 1 / 6 * max(abs(roi_dct[1, 0] - roi_dct[0, 1] - roi_dct[1, 1]), abs(roi_dct[0, 1] - roi_dct[1, 0] - roi_dct[1, 1])) # thetaNE = gamma*abs(roi_dct[1, 1]) thetaNE = gamma # print([thetaNE, theta0, theta45, theta90, theta135]) return [thetaNE, theta0, theta45, theta90, theta135]
def block_get_wm(self, block, index): block_dct = cv2.dct(block) block_dct_flatten = block_dct.flatten().copy() block_dct_flatten = block_dct_flatten[index] block_dct_shuffled = block_dct_flatten.reshape(self.block_shape) U, s, V = np.linalg.svd(block_dct_shuffled) max_s = s[0] wm_1 = 255 if max_s % self.mod > self.mod / 2 else 0 if self.mod2: max_s = s[1] wm_2 = 255 if max_s % self.mod2 > self.mod2 / 2 else 0 wm = (wm_1 * 3 + wm_2 * 1) / 4 else: wm = wm_1 return wm
def _dct_img(self, img): """ return dct of specified matrix :param img: np.ndarray of self.GRAYSCALE_CONTAINER_TYPE :return: np.ndarray of self.DCT_CONTAINER_TYPE """ ret = np.ndarray((self.size_b_h, self.size_b_w), dtype=np.dtype((self.DCT_CONTAINER_TYPE, (8, 8)))) block = np.zeros((8, 8), dtype=self.DCT_CONTAINER_TYPE) for r, c in self.block_coordinates: block[:8, :8] = img[r:r + 8, c:c + 8] # dct argument must be matrix of float ret[r / 8, c / 8][:, :] = cv2.dct(block) return ret
def _idct2(imgflt_stack): """ Discrete cosine transform This function originally existed to replicate Matlabs dct function using scipy's dct function. It was necessary to perform the dct along the rows and columns. To simplify the container creation, the dct function from opencv was used. This function is slower, and scipy's version should be implemented in the future. The scipy dct that was originally used was type-III, which is the inverse of dct type-II Inputs: imgflt_stack - Input matrix to perform dct on Outputs: d - The dct of input, imgflt_stack """ d = cv2.dct(imgflt_stack, flags=cv2.DCT_INVERSE).astype(np.float64) return d
def get_hash(img): # Resize them to 8x8 imgresize = cv2.resize(img, (8, 8)) imgresize = cv2.cvtColor(imgresize, cv2.COLOR_BGR2GRAY) imgdct = cv2.dct(np.float32(imgresize) / 255.0) # Calculate average DCT imgavdct = average2D(imgdct) # Hash the DCT imgdcthash = hashTable(imgdct, imgavdct) # Generage the hash Value imgvalue = concatenation(imgdcthash) return imgvalue
def __compute_phash__(self, image): """ Computes pHash based on discrete cosine transformation. Implemantation based on http://www.hackerfactor.com/blog/index.php?/archives/432-Looks-Like-It.html Args: image(numpy.ndarray): Image from which to compute the hash Returns: numpy.ndarray: 2D binary array with computed pHash """ gray = cv.cvtColor(image, cv.COLOR_BGR2GRAY) resized = cv.resize(gray, (32, 32), interpolation=cv.INTER_AREA) dct = cv.dct(np.float32(resized)) dct = np.uint8(dct) dct_low_freq = dct[:8, :8] med = np.median(dct_low_freq) ret = dct_low_freq > med return ret.flatten()
def p_hash(img, convert): """Create pHash string from given image.""" big_kernel = 32 small_kernel = int(big_kernel / 4) img = _get_shrinked_grayscale(img, big_kernel, big_kernel, convert) img = np.float32(img) / 255.0 img = cv2.dct(img) average = _get_top_left_average(img, small_kernel) hash_string = [] for i in range(small_kernel): for j in range(small_kernel): if (img[i][j] < average): hash_string.append('1') else: hash_string.append('0') return ''.join(hash_string)
def dct_demo(crop=True, cmap='flag', asset='assets/parrot.png'): img1 = cv2.imread(asset, cv2.CV_LOAD_IMAGE_UNCHANGED) # convert image to YCrCb and drop the color channels if len(img1) > 1: # color image transcol = cv2.cvtColor(img1, cv2.cv.CV_BGR2YCrCb) channel = transcol[:, :, 0] else: channel = img1 if crop: BLOCKSIZE = (64, 64) # crop a 128x128 block and resize it in half: crop = channel[35:163, 103:231] crop = cv2.resize(crop, BLOCKSIZE) else: crop = channel[::, ::] BLOCKSIZE = channel.shape plt.figure(1) plt.subplot(1, 2, 1) plt.imshow(crop, cmap='gray') plt.title('Image section') # do the quantization: vis0 = np.zeros(BLOCKSIZE, np.float32) vis0[::, ::] = crop # shift the values to signed vis0 = vis0 - 128 # DCT convert it currentblock = cv2.dct(vis0) # save the image: # cv2.cv.SaveImage('Transformed.png', cv2.cv.fromarray(currentblock)) plt.subplot(1, 2, 2) plt.imshow(currentblock, cmap=cmap) plt.title('DC Transformed Image section') plt.draw() return currentblock
def genkframe(seed): np.random.seed(seed) keys = [] for j in range(256): v = [] for i in range((1 + 30) * 30 // 2): v.append(np.random.normal(0,10000)) keys.append(v) keys = np.array(keys) keys = gs(keys) * 1000 kframes = [] for key in keys: print(np.max(key)) print(np.min(key)) d = genpat(key) kframe = cv2.dct(d,cv2.DCT_INVERSE) kframes.append(kframe) print(np.max(kframe)) print(np.min(kframe)) #cv2.imshow('d',(kframe + 128).astype('uint8')) #cv2.waitKey(0) return kframes
def jpegCompress(image, quantmatrix): ''' Compress(imagefile, quanmatrix simulates the lossy compression of baseline JPEG, by quantizing the DCT coefficients in 8x8 blocks ''' # Return compressed image in result H = np.size(image, 0) W = np.size(image, 1) # Number of 8x8 blocks in the height and width directions h8 = H / 8 w8 = W / 8 # TODO If not an integer number of blocks, pad it with zeros h8_t = h8 if H%8 is 0 else h8+1 w8_t = w8 if W%8 is 0 else w8+1 im_t = np.zeros((h8_t*8,w8_t*8,1),dtype=np.float32) im_t[:H,:W,0] = im[:,:,0]*0.114+im[:,:,1]*0.587+im[:,:,2]*0.299 # TODO Separate the image into blocks, and compress the blocks via quantization DCT coefficients DCT_arr = [] for i in xrange(h8_t): list = [] for j in xrange(w8_t): tmp = (cv2.dct(im_t[i*8:(i+1)*8,j*8:(j+1)*8,:])/quantmatrix+0.5) tmp = tmp.astype(np.uint8) tmp = tmp.astype(np.float32) list.append( tmp ) DCT_arr.append(list) # TODO Convert back from DCT domain to RGB image for i in xrange(h8_t): for j in xrange(w8_t): im_t[i*8:(i+1)*8,j*8:(j+1)*8,0] = cv2.idct( DCT_arr[i][j] ) result =np.zeros((h8_t*8,w8_t*8,3),dtype=np.float32) result[:,:,0] = result[:,:,1] = result[:,:,2] = im_t[:,:,0] result=result.astype(np.uint8) return result
def signature_saliency(img): """ Signature Saliency. X. Hou, J. Harel, and C. Koch, "Image Signature: Highlighting Sparse Salient Regions." IEEE Trans. Pattern Anal. Mach. Intell. 34(1): 194-201 (2012) """ old_shape = (img.shape[0],img.shape[1]) img = img_padded_for_dct(img) img = img/255.0 sal = [] for c in range(img.shape[2]): channel = img[:,:,c].astype(np.dtype('float32')) channel_dct = np.sign(cv2.dct(channel)) s = cv2.idct(channel_dct) s = np.multiply(s,s) sal.append(s) sal = sum(sal)/3.0 sal = cv2.GaussianBlur(sal, (11,11), 0) sal = sal[:old_shape[0], :old_shape[1]] return sal
def parrot(show=False): """ This function uses the JPEG 8x8 Blocksize and creates full size frames. """ B = 8 img1 = cv2.imread('assets/parrot.png', cv2.CV_LOAD_IMAGE_UNCHANGED) # we only use the gray channel transcol = cv2.cvtColor(img1, cv2.cv.CV_BGR2YCrCb) channel = transcol[:, :, 0] # In the following loop the image is DCT converted block by block. # Quantization of 'quality' is applied. plt.figure() plt.subplot(1, 2, 1) plt.imshow(channel, cmap='gray') plt.title('Original Image') channelrows = channel.shape[0] channelcols = channel.shape[1] trans = np.zeros((channelrows, channelcols), np.float32) trans_quant = np.zeros((channelrows, channelcols), np.float32) blocksV = channelrows/B blocksH = channelcols/B vis0 = np.zeros((channelrows, channelcols), np.float32) vis0[:channelrows, :channelcols] = channel vis0 = vis0 - 128 for row in range(blocksV): for col in range(blocksH): currentblock = cv2.dct(vis0[row*B:(row+1)*B, col*B:(col+1)*B]) trans[row*B:(row+1)*B, col*B:(col+1)*B] = currentblock plt.subplot(1, 2, 2) plt.imshow(trans, cmap='flag') # plt.colorbar(shrink=0.5) plt.title('DCT of Y') if show: plt.show() return trans
def _run_(self): ''' ''' print '- Running Encoder...' hf = h.HuffCoDec() flnm = self.filepath.split('/')[-1:][0].split('.')[0] + '.huff' fo = open(flnm,'w') fo.write(str(self.Mo) + ',' + str(self.No) + ',' + str(self.Do) + ',' + str(self.qually) + ',' + self.mode + '\n') dYmg = self.Ymg - 128 r, c, chnl = self.r, self.c, self.NCHNL coefs = np.zeros((r, c, chnl)) seqhuff = '' #nbits = self.NumBits if self.mode == '444': for ch in range(chnl): DCant = 0 for i in range(self.nBlkRows): for j in range(self.nBlkCols): sbimg = dYmg[r*i:r*i+r, c*j:c*j+c, ch] #Subimagens nxn # TRANSFORMADA - Aplica DCT coefs = cv2.dct(sbimg) # QUANTIZAÇÃO/LIMIARIZAÇÃO zcoefs = np.round( coefs/self.Z[:,:,ch] ) #Coeficientes normalizados - ^T(u,v)=arred{T(u,v)/Z(u,v)} # CODIFICAÇÃO - Codigos de Huffman # - FOWARD HUFF seq = h.zigzag(zcoefs) #Gera Sequencia de coeficientes 1-D hfcd = hf.fwdhuff(DCant, seq, ch) #Gera o codigo huffman da subimagem DCant = seq[0] self.NumBits += hfcd[0] seqhuff += hfcd[1] #Salvar os codigos em arquivo fo.write(seqhuff+'\n') seqhuff = '' elif self.mode == '420': if chnl == 1: Ymg = dYmg else: Y = dYmg[:,:,0] dims, CrCb = h.adjImg(downsample(dYmg[:,:,1:3], self.mode)[1]) Ymg = [ Y, CrCb[:,:,0], CrCb[:,:,1] ] self.lYmg = Ymg for ch in range(chnl): DCant = 0 if ch == 0: #LUMINANCIA rBLK = self.nBlkRows cBLK = self.nBlkCols else: #CROMINANCIA rBLK, cBLK = int(np.floor(dims[0]/self.r)), int(np.floor(dims[1]/self.c)) for i in range(rBLK): for j in range(cBLK): sbimg = Ymg[ch][r*i:r*i+r, c*j:c*j+c] #Subimagens nxn # TRANSFORMADA - Aplica DCT coefs = cv2.dct(sbimg) # QUANTIZAÇÃO/LIMIARIZAÇÃO zcoefs = np.round( coefs/self.Z[:,:,ch] ) #Coeficientes normalizados - ^T(u,v)=arred{T(u,v)/Z(u,v)} # CODIFICAÇÃO - Codigos de Huffman - FOWARD HUFF seq = h.zigzag(zcoefs) #Gera Sequencia de coeficientes 1-D hfcd = hf.fwdhuff(DCant, seq, ch) #Gera o codigo huffman da subimagem DCant = seq[0] self.NumBits += hfcd[0] seqhuff += hfcd[1] #Salvar os codigos em arquivo fo.write(seqhuff + '\n') seqhuff = '' fo.close() self.avgBits = (float(self.NumBits)/float(self.Mo*self.No)) self.CRate = 24./self.avgBits self.Redunc = 1.-(1./self.CRate) print '- Encoder Complete...'
cv2.namedWindow('dct after',0) cv2.namedWindow('low freq suppressed',0) cv2.namedWindow('bring out black gaps',0) cv2.namedWindow('connect them together',0) cv2.namedWindow('auto thresh',0) cv2.namedWindow('boxmask',0) cv2.namedWindow('done',0) img = cv2.imread('./out_hor.jpg') gray=cv2.cvtColor(img,cv2.COLOR_BGR2GRAY) orig=gray.copy() gray = gray.astype('float32') gray/=255 dct=cv2.dct(gray) dctvis=cv2.normalize(np.log(dct.copy()),-1,0,1,cv2.NORM_MINMAX) cv2.imshow('dct before',dctvis) vr=1.#vertical ratio, how much percentage of vertical freq components should be thrown away hr=.95#horizontal dct[0:vr*dct.shape[0],0:hr*dct.shape[1]]=0 dctvis=cv2.normalize(np.sqrt(dct.copy()),-1,0,1,cv2.NORM_MINMAX) cv2.imshow('dct after',dctvis) gray=cv2.idct(dct) gray=cv2.normalize(gray,-1,0,1,cv2.NORM_MINMAX) gray*=255 gray=gray.astype('uint8')
def get_dct(array): """ Will raise TypeError on odd dim's arrays. """ return cv2.dct(array)