目前支持检测的类别有:黑场、模糊、雪花、静帧、夹帧
# coding=utf-8
import cv2
import numpy as np
from scipy import stats
def black_filter(img_hsv, black_var_limit=1000, black_mean_limit=50):
V = img_hsv[:, :, 2]
V_var = np.var(V)
V_mean = np.mean(V)
# print('>>>', V_var, V_mean)
if V_var > black_var_limit and V_mean > black_mean_limit: # 黑场
return True
return False
def burt_filter(img, burt_var_limit=2500): # 模糊检测
gray = cv2.cvtColor(img, cv2.COLOR_RGB2GRAY)
gray_var = cv2.Laplacian(gray, cv2.CV_64F).var() # 图像模糊度
# print(gray_var, gray_var < burt_var_limit)
if gray_var < burt_var_limit: # 模糊
return True
return False
def snow_filter(img_hsv, snow_limit=1e-20):
V = img_hsv[:, :, 2]
V_var = np.std(V)
V_mean = np.mean(V)
try:
ss = stats.kstest(V, 'norm', (V_mean, V_var)) # KS检验
if ss.pvalue > snow_limit: # 雪花
return True
return False
except:
return False
def rtsp_filter(frame_list_3, limit1=0, limit2=2500):
"""
:param frame_list_3: 前三帧列表
:param limit1: 帧间方差阈值-min
:param limit2: 帧间方差阈值-max
:return: 0:正常,1:静帧,2:夹帧,3:黑场,4:模糊,5:雪花,顺序:3>4>5>1>2>0
"""
frame_now = frame_list_3[-1]
frame_hsv = cv2.cvtColor(frame_now, cv2.COLOR_BGR2HSV)
if black_filter(frame_hsv):
return 3
elif burt_filter(frame_now):
return 4
elif snow_filter(frame_hsv):
return 5
else:
pass
diff1 = np.array(frame_list_3[0], dtype='int8') - np.array(frame_list_3[1], dtype='int8')
diff2 = np.array(frame_list_3[1], dtype='int8') - np.array(frame_list_3[2], dtype='int8')
diff1_var = np.var(diff1)
diff2_var = np.var(diff2)
if diff1_var <= limit1 and diff2_var <= limit1: # 静帧
return 1
elif diff1_var > limit2 and diff2_var > limit2: # 夹帧
return 2
else:
return 0
def main(video_source='test.mp4', side=400):
capture = cv2.VideoCapture(video_source)
zeros = np.zeros((side, side))
frame_list_3 = [zeros, zeros, zeros]
warns = ['正常', '静帧', '夹帧', '黑场', '模糊', '雪花']
cnt = 0
while True:
status, frame = capture.read()
frame = cv2.resize(frame, (side, side))
frame_list_3.pop(0)
frame_list_3.append(frame)
sign = rtsp_filter(frame_list_3)
if not sign:
print('第{}帧: ', warns[sign])
cnt += 1
capture.release()
if __name__ == '__main__':
main()