123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193 |
- # encoding: utf-8
- import cv2 as cv
- import numpy as np
- import math
- #裁剪图片
- def cutImage(img_addr):
- img = cv.imread(img_addr)
- img_arr = np.array(img)
- hight = img_arr.shape[0]
- wight = img_arr.shape[1]
- dest_img = img_arr[hight/2+20:hight,wight/2:wight,:]
- return dest_img
- def cmpPicWithRGB(picPath1,picPath2):
- std_img = cutImage(picPath1)
- test_img = cutImage(picPath2)
- width = std_img.shape[0]
- hight = test_img.shape[1]
- std_B, std_G, std_R = cv.split(std_img)
- test_B, test_G, test_R = cv.split(std_img)
- sum_std_B = 0
- sum_std_G = 0
- sum_std_R = 0
- for x in range(0,width,1):
- for y in range(0,hight,1):
- sum_std_B = sum_std_B + std_B[x][y]
- sum_std_G = sum_std_G + std_G[x][y]
- sum_std_R = sum_std_R + std_R[x][y]
- avg_std_B = sum_std_B / (width*hight)
- avg_std_G = sum_std_G / (width*hight)
- avg_std_R = sum_std_R / (width*hight)
- for x in range(0,width,1):
- for y in range(0,hight,1):
- if abs(test_B[x][y] - avg_std_B) >10 or abs(test_G[x][y] - avg_std_G) > 10 or abs(test_R[x][y] - avg_std_R[x][y] > 10):
- print test_B[x][y]
- print test_G[x][y]
- print test_R[x][y]
- print avg_std_B
- print avg_std_R
- print avg_std_G
- return False
- else:
- return True
- class RGBColor():
- def __init__(self):
- pass
- '''
- BGR颜色差值小于offset值时,定性为灰阶色调。
- '''
- def isGray(self, bgr, offset = 10):
- # print "RGB isGray:", bgr,abs(bgr[0] - bgr[1])
- if abs(bgr[0] - bgr[1]) < offset \
- and abs(bgr[1] - bgr[2]) < offset\
- and abs(bgr[2] - bgr[0]) < offset:
- return True
- else:
- return False
- '''
- 传入的图片对象,必须是BGR颜色空间。
- 根据BGR颜色值,判断是否为纯色图片。同时忽略极少的噪点干扰。
- :param img:传入的图片对象, BGR颜色空间
- :param expTh: 颜色平均值偏差范围,> expTh 则是False。
- :return: [判断结果True/False,颜色值]
- '''
- def isSingleColor(self, img, expTh=0.01, splitCount=10):
- height, width, color = img.shape
- heightStep = height/splitCount
- widthStep = width/splitCount
- totalAvg = self.getAvgBGR(img)
- expCount = 0.0
- for heightCount in range(0,splitCount):
- for widthCount in range(0, splitCount):
- height0 = heightStep*heightCount
- width0 = widthStep*widthCount
- height1 = height0+heightStep
- width1 = width0+widthStep
- scaleAvg = self.getAvgBGR(img[height0:height1, width0:width1])
- ret = self.isColorSimilar(totalAvg, scaleAvg, faultTolerance=40)
- if ret is False:
- expCount += 1
- expRate = expCount/(splitCount*splitCount)
- print "isSingleColor,expRate:",expRate,expCount
- if expRate > expTh:
- return False, totalAvg
- else:
- return True, totalAvg
- def getAvgBGR(self, img):
- imgB = img[:,:,0]
- imgG = img[:,:,1]
- imgR = img[:,:,2]
- avgB = np.average(imgB)
- avgG = np.average(imgG)
- avgR = np.average(imgR)
- return avgB,avgG,avgR
- def getMaxBGR(self, img):
- imgB = img[:, :, 0]
- imgG = img[:, :, 1]
- imgR = img[:, :, 2]
- maxB = np.max(imgB)
- maxG = np.max(imgG)
- maxR = np.max(imgR)
- return maxB, maxG, maxR
- '''
- 判断一张图片是否是纯黑图片。
- :param img:需要判断的图片
- :param grayTH : 黑色判断的灰阶阈值
- :param splitCount: 图片拆分的行列次数
- :param expTh:黑色计算的容错区域比例。> expTh 则是False。
- '''
- def isBlack(self, img, grayTH = 70,splitCount=10, expTh = 0.01):
- height, width, color = img.shape
- heightStep = height / splitCount
- widthStep = width / splitCount
- totalAvg = self.getAvgBGR(img)
- expCount = 0.0
- for heightCount in range(0, splitCount):
- for widthCount in range(0, splitCount):
- height0 = heightStep * heightCount
- width0 = widthStep * widthCount
- height1 = height0 + heightStep
- width1 = width0 + widthStep
- scaleAvg = self.getAvgBGR(img[height0:height1, width0:width1])
- ret = self.isGray(scaleAvg)
- #print "rgb isBlack,gray ret:", ret
- if ret is False or scaleAvg[1] > grayTH:
- expCount += 1
- expRate = expCount / (splitCount * splitCount)
- print "isBlack,expRate:", expRate, expCount
- if expRate > expTh:
- return False
- else:
- return True
- '''
- # 描述:bgr色差计算。ΔE=( ΔL^2 + ΔA^2 + ΔB^2 ) ^ (1/2) ΔE
- # 参数:color1、color2: bgr格式
- # 返回值:
- # 相差值,越小越相近。
- # 0~50(微小色差),感觉极微;
- # 50~150(小色差),感觉轻微;
- # 150~300(较小色差),感觉明显;
- # 300~600(较大色差),感觉很明显;
- # 600以上(大色差),感觉强烈。
- # '''
- def colorDistance(self, color1, color2):
- b1, g1, r1 = color1
- b2, g2, r2 = color2
- rmean = (r1 + r2) / 2
- R = int(r1) - int(r2)
- G = int(g1) - int(g2)
- B = int(b1) - int(b2)
- return math.sqrt((2 + rmean / 256) * (R ** 2) + 4 * (G ** 2) + (2 + (255 - rmean) / 256) * (B ** 2))
- '''
- # 描述:颜色是否相近。
- # 参数:
- # color1、color2: bgr格式
- # faultTolerance: 容错值大小,表示两颜色的色差值
- # 返回值:<= faultTolerance返回True,否则返回False.
- #
- # '''
- def isColorSimilar(self, color1, color2, faultTolerance=100):
- if 0:
- b1 = color1[0] in range(color2[0] - faultTolerance, color2[0] + faultTolerance)
- b2 = color1[1] in range(color2[1] - faultTolerance, color2[1] + faultTolerance)
- b3 = color1[2] in range(color2[2] - faultTolerance, color2[2] + faultTolerance)
- if b1 == True and b2 == True and b3 == True:
- return True
- else:
- return False
- if 1:
- val = self.colorDistance(color1, color2)
- return True if val <= faultTolerance else False
|