pq_detect.py 6.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169
  1. # -*- coding:utf-8 -*-
  2. from RGB import *
  3. from image_util import *
  4. import os, sys, time
  5. import cv2 as cv
  6. import numpy as np
  7. import random
  8. class PQDetect():
  9. def __init__(self):
  10. self.RGBColor = RGBColor()
  11. def isSnowPic2(self, pic_path):
  12. im1 = cv.imread(pic_path)
  13. h1, w1, c1 = im1.shape
  14. print h1, w1, c1
  15. im1_1 = im1[0:h1 / 2, 0:w1 / 2]
  16. im1_2 = im1[0:h1 / 2, w1 / 2:w1]
  17. im1_3 = im1[h1 / 2:h1, 0:w1 / 2]
  18. im1_4 = im1[h1 / 2:h1, w1 / 2:w1]
  19. hist_list = []
  20. hist_list.append(cv.calcHist([im1_1], [0], None, [256], [0, 256]))
  21. hist_list.append(cv.calcHist([im1_2], [0], None, [256], [0, 256]))
  22. hist_list.append(cv.calcHist([im1_3], [0], None, [256], [0, 256]))
  23. hist_list.append(cv.calcHist([im1_4], [0], None, [256], [0, 256]))
  24. count = 0
  25. totalHist = 0
  26. for hist_1 in hist_list:
  27. for hist_2 in hist_list:
  28. diffHist = cv.compareHist(hist_1, hist_2, cv.HISTCMP_BHATTACHARYYA)
  29. if diffHist <> 0:
  30. count += 1
  31. totalHist += diffHist
  32. four_zone_diff = totalHist / count
  33. print four_zone_diff
  34. rhist = cv.calcHist([im1_1], [0], None, [256], [0, 256])
  35. bhist = cv.calcHist([im1_2], [2], None, [256], [0, 256])
  36. bgr_diff = cv.compareHist(rhist, bhist, cv.HISTCMP_BHATTACHARYYA)
  37. print bgr_diff
  38. if four_zone_diff < 0.1 and bgr_diff < 0.2:
  39. return True
  40. else:
  41. return False
  42. '''
  43. 判断传入的图片,是否为ATV无信号雪花屏。定义雪花屏:清晰度25左右.然后随机取20个区域,查看直方图趋势相似度。
  44. :param pic_path:图片路径
  45. :threshold: 直方图差异临界值。 范围 0 ~ 1
  46. :sharpDiff: 清晰度容错范围值。
  47. :return : True代表是雪花屏,False代表不是雪花屏
  48. '''
  49. def isSnowPic(self, pic_path, threshold=0.1, sharpDiff=10, sharpSnow = 25):
  50. im1 = cv.imread(pic_path)
  51. h1, w1, c1 = im1.shape
  52. sharpP = self.detSharpLaplacian(pic_path)
  53. hist_list = []
  54. for i in range(20):
  55. x1 = random.randint(0,h1/2)
  56. y1 = random.randint(0,w1/2)
  57. rect_h = h1/2
  58. rect_w = w1/2
  59. # print [x1,y1, x1+ rect_w, y1+rect_h]
  60. im = cutMat(im1, [x1,y1, x1+ rect_h, y1+rect_w])
  61. hist = cv.calcHist([im], [0], None, [256], [0, 256])
  62. hist_list.append(hist)
  63. count = 0
  64. totalHist = 0
  65. for hist_1 in hist_list:
  66. for hist_2 in hist_list:
  67. diffHist = cv.compareHist(hist_1, hist_2, cv.HISTCMP_BHATTACHARYYA)
  68. if diffHist <> 0:
  69. count += 1
  70. totalHist += diffHist
  71. four_zone_diff = totalHist / count
  72. print "isSnowPic:", four_zone_diff,sharpP
  73. if four_zone_diff < threshold and abs(sharpP - sharpSnow) <= sharpDiff:
  74. return True
  75. else:
  76. return False
  77. '''
  78. 根据传入的图片路径,计算图片色温
  79. '''
  80. def calculateCCT(self, pic_path):
  81. img = cv.imread(pic_path)
  82. xyImg = cv.cvtColor(img,cv.COLOR_BGR2XYZ)
  83. #色温计算
  84. X = np.average(xyImg[:,:,0])
  85. Y = np.average(xyImg[:,:,1])
  86. Z = np.average(xyImg[:,:,2])
  87. x = X/(X+Y+Z) #色谱XYZ转换成色坐标x
  88. y = Y/(X+Y+Z) #色谱XYZ转换成色坐标y
  89. print "calculateCCT,x,y:",x,y
  90. n = (x-0.3320)/(0.1858-y)
  91. print "calculateCCT,n:",n
  92. CCT = 437*n**3 + 3601*n**2 + 6831*n + 5517
  93. print "calculateCCT,CCT:",CCT
  94. return CCT
  95. '''
  96. Tenengrad梯度方法利用Sobel算子分别计算水平和垂直方向的梯度,同一场景下梯度值越高,图像越清晰。
  97. 以下是具体实现,这里衡量的指标是经过Sobel算子处理后的图像的平均灰度值,值越大,代表图像越清晰。
  98. :param 图片路径
  99. :return float, 值越大,代表清晰度越高
  100. '''
  101. def detSharpTenengrad(self, pic_path):
  102. img = cv.imread(pic_path)
  103. grayImg = cv.cvtColor(img, cv.COLOR_BGR2GRAY)
  104. sobelImg = cv.Sobel(grayImg, cv.CV_16U, 1, 1)
  105. grayV = cv.mean(sobelImg)[0] # 图像的平均灰度
  106. # cv.putText(img, str(grayV), (20,50), cv.FONT_HERSHEY_COMPLEX, 0.8, (255,255,0))
  107. # cv.imshow("清晰度",img)
  108. # cv.waitKey(0)
  109. return grayV
  110. '''
  111. 采用Laplacian梯度方法检测清晰度
  112. :param 图片路径
  113. :return float, 值越大,代表清晰度越高
  114. '''
  115. def detSharpLaplacian(self, pic_path):
  116. img = cv.imread(pic_path)
  117. return self.detImgSharpLaplacian(img)
  118. def detImgSharpLaplacian(self, img):
  119. grayImg = cv.cvtColor(img, cv.COLOR_BGR2GRAY)
  120. sobelImg = cv.Laplacian(grayImg, cv.CV_16U)[0]
  121. grayV = cv.mean(sobelImg)[0] # 图像的平均灰度
  122. # cv.putText(img, str(grayV), (20, 50), cv.FONT_HERSHEY_COMPLEX, 0.8, (255, 255, 0))
  123. # cv.imshow("清晰度", img)
  124. # cv.waitKey(0)
  125. return grayV
  126. '''
  127. 采用方差(Variance)方法检测清晰度。
  128. 方差是概率论中用来考察一组离散数据和其期望(即数据的均值)之间的离散(偏离)成都的度量方法。
  129. 方差较大,表示这一组数据之间的偏差就较大,组内的数据有的较大,有的较小,分布不均衡;
  130. 方差较小,表示这一组数据之间的偏差较小,组内的数据之间分布平均,大小相近。
  131. :param 图片路径
  132. :return float, 值越大,代表清晰度越高
  133. '''
  134. def detSharpVariance(self, pic_path):
  135. img = cv.imread(pic_path)
  136. grayImg = cv.cvtColor(img, cv.COLOR_BGR2GRAY)
  137. # 求灰度图像的标准差
  138. stdValueImg = cv.meanStdDev(grayImg)
  139. # print stdValueImg
  140. meanValue = stdValueImg[1][0][0] # 求得均方差。stdValueImg:(均差array([[ 16.58646894]]), 标准差array([[ 10.1834467]]))
  141. grayV = meanValue * meanValue
  142. # cv.putText(img, str(grayV), (20, 50), cv.FONT_HERSHEY_COMPLEX, 0.8, (255, 255, 0))
  143. # cv.imshow("清晰度", img)
  144. # cv.waitKey(0)
  145. return grayV