def get_valid_box(image, points): """ Try to get a valid face box which meets the requirments. The function follows these steps: 1. Try method 1, if failed: 2. Try method 0, if failed: 3. Return None """ # Try method 1 first. def _get_postive_box(raw_boxes, points): for box in raw_boxes: # Move box down. diff_height_width = (box[3] - box[1]) - (box[2] - box[0]) offset_y = int(abs(diff_height_width / 2)) box_moved = move_box(box, [0, offset_y]) # Make box square. square_box = get_square_box(box_moved) # Remove false positive boxes. if points_in_box(points, square_box): return square_box return None # Try to get a positive box from face detection results. _, raw_boxes = fd.get_facebox(image, threshold=0.5) positive_box = _get_postive_box(raw_boxes, points) if positive_box is not None: if box_in_image(positive_box, image) is True: return positive_box return fit_box(positive_box, image, points)
def extract_face(file, tail, count): """Extract face area from image.""" image = read_image(file) conf, raw_boxes = fd.get_facebox(image=image, threshold=0.9) # fd.draw_result(image, conf, raw_boxes) for box in raw_boxes: # Move box down. diff_height_width = (box[3] - box[1]) - (box[2] - box[0]) offset_y = int(abs(diff_height_width / 2)) box_moved = pt.move_box(box, [0, offset_y]) # Make box square. facebox = pt.get_square_box(box_moved) face_image = image[facebox[1]:facebox[3], facebox[0]:facebox[2]] # Save the Image. image_url = os.path.join(TARGET_DIR, str(count) + '-' + tail) if face_image.shape[0] * face_image.shape[1] != 0: preview_img = face_image.copy() preview_img = cv2.resize(preview_img, (512, 512)) cv2.imshow('preview', preview_img) if cv2.waitKey() == 27: face_image = cv2.resize(face_image, (128, 128)) cv2.imwrite(image_url, face_image) print("New file saved:", image_url) count += 1 return face_image
def preview(point_file): """ Preview points on image. """ # Read the points from file. raw_points = read_points(point_file) # Safe guard, make sure point importing goes well. assert len(raw_points) == 68, "The landmarks should contain 68 points." # Read the image. head, tail = os.path.split(point_file) image_file = tail.split('.')[-2] img_jpg = os.path.join(head, image_file + ".jpg") img_png = os.path.join(head, image_file + ".png") if os.path.exists(img_jpg): img = cv2.imread(img_jpg) else: img = cv2.imread(img_png) #Faust add+[ conf, facebox = fd.get_facebox(img, threshold=0.5) fd.draw_result(img, conf, facebox) #Faust add+] # Fast check: all points are in image. if points_are_valid(raw_points, img) is False: return None # Get the valid facebox. facebox = get_valid_box(img, raw_points) if facebox is None: print("Using minimal box.") facebox = get_minimal_box(raw_points) # fd.draw_box(img, [facebox], box_color=(255, 0, 0)) # Extract valid image area. face_area = img[facebox[1]:facebox[3], facebox[0]:facebox[2]] # Check if resize is needed. width = facebox[2] - facebox[0] height = facebox[3] - facebox[1] if width != height: print('opps!', width, height) if (width != 128) or (height != 128): face_area = cv2.resize(face_area, (256, 256)) # Show the result. cv2.imshow("face", face_area) if cv2.waitKey(10) == 27: cv2.waitKey()
def extract_face(image): conf, raw_boxes = fd.get_facebox(image=image, threshold=0.9) for box in raw_boxes: diff_height_width = (box[3] - box[1]) - (box[2] - box[0]) offset_y = int(abs(diff_height_width / 2)) box_moved = pt.move_box(box, [0, offset_y]) facebox = pt.get_square_box(box_moved) if pt.box_in_image(facebox, image): return facebox return None
def extract_face(file): global new_img """Extract face area from image.""" image = read_image(file) conf, raw_boxes = fd.get_facebox(image=image, threshold=0.9) # fd.draw_result(image, conf, raw_boxes) for box in raw_boxes: # Move box down. diff_height_width = (box[3] - box[1]) - (box[2] - box[0]) offset_y = int(abs(diff_height_width / 2)) box_moved = pt.move_box(box, [0, offset_y]) # Make box square. facebox = pt.get_square_box(box_moved) face_image = image[facebox[1]:facebox[3], facebox[0]:facebox[2]] if face_image.shape[0] * face_image.shape[1] != 0: preview_img = face_image.copy() new_img = cv2.resize(preview_img, (128, 128)) return new_img
def change_box(img, DATA_DIR, pointThr=40): ''' 实现框的转换,使其只剩下有特征点标记的框以及改变其大小,使其能包含所有的框 :param img: 图片 :pointthr:超过多少个点在框里判定这个框为有效框 :data_dir:数据路径 :return: 新的框的坐标 ''' confidences, faceboxes = fd.get_facebox(img, 0.5) points = pt.read_points(DATA_DIR) newFacebox = [] m = 0 for i in faceboxes: for j in points: if ((i[0] < j[0] < i[2]) and (i[1] < j[1] < i[3])): m = m + 1 if m > pointThr: newFacebox.append(i) m = 0 # print(faceboxes) # print(newFacebox) # print("$$$$$$$$$") newConf = [confidences[faceboxes.index(newFacebox[0])]] left_x, left_y, right_x, right_y = newFacebox[0] #将边界框的位置总体向下移动,移动的大小为边界框的高度与宽度之差的一半 height = right_y - left_y width = right_x - left_x left_y = left_y + (height - width) / 2 right_y = right_y + (height - width) / 2 #使得其变为正方形 if height != width: left_x = left_x - (height - width) / 2 right_x = right_x + (height - width) / 2 newFacebox = [[int(left_x), int(left_y), int(right_x), int(right_y)]] # print(newConf,newFacebox) return newConf, newFacebox
def process(video_dir, save_dir, train_file_list): minsize = 20 #error = # if not os.path.exists(train_file_list): # head, tail = os.path.split(train_file_list) # os.makedirs(head) total_face = 0 with open(train_file_list, 'a+') as f_trainList: for dir_path, dir_names, _ in os.walk(video_dir): # frame_count = 0 for dir_name in dir_names: print('processing directory: ' + dir_path + '/' + dir_name) video_dir_name = os.path.join(dir_path, dir_name) if dir_name in ['Normal']: label = '0' elif dir_name in ['Talking']: label = '0' elif dir_name in ['Yawning']: label = '1' else: print("Too bad, label invalid.") continue video_names = os.listdir(video_dir_name) for video_name in video_names: # video = cv2.VideoCapture() frame_count = -1 cap = cv2.VideoCapture(os.path.join(video_dir_name, video_name)) if cap.isOpened(): ftotal = cap.get(cv2.CAP_PROP_FRAME_COUNT) read_success = True else: read_success = False # cv2.imwrite(img_save_path, img) while read_success: read_success, img = cap.read() try: img.shape except: break frame_count += 1 if frame_count % SAMPLE_STEP == 0: # img = img.transpose(2, 0, 1) conf, raw_boxes = fd.get_facebox(image=img, threshold=0.7) if len(raw_boxes) == 0: # if face can't be detected between n frames print('***too sad, the face can not be detected!') continue elif len(raw_boxes) == 1: bbox = raw_boxes[0] elif len(raw_boxes) > 1: #print('---multi detect!') # idx = np.argsort(-raw_boxes[:, 4]) # TODO. sort bbox = raw_boxes[0] bbox = rectify_bbox(bbox, img) x = int(bbox[0]) y = int(bbox[1]) w = int(bbox[2] - bbox[0]) h = int(bbox[3] - bbox[1]) face = img[y:y + h, x:x + w, :] # cv2.imwrite('face.jpg', face) face_sp = np.shape(face) #if face_sp[0] <= 16 or face_sp[1] <= 16: # continue face_resize = face face_resize = cv2.resize(face_resize, (CROPPED_WIDTH, CROPPED_HEIGHT)) if DEBUG: cv2.imshow('face', face) ch = cv2.waitKey(40000) & 0xFF cv2.imshow('face_trans', face_resize) ch = cv2.waitKey(40000) & 0xFF img = drawBoxes(img, bbox) # for i in range(5): # cv2.circle(img, (point[i], point[5+i]), 2, [0, 0, 255]) cv2.imshow('img', img) ch = cv2.waitKey(40000) & 0xFF if ch == 27: break total_face += 1 img_file_name = video_name.split('.')[0] img_file_name = img_file_name + '-' + str(total_face) + '_' + str(label) + '.jpg' # f_trainList.write(img_file_name + ' ' + label + '\n') img_save_path = os.path.join(save_dir, img_file_name) f_trainList.write(img_save_path + ' ' + label + '\n') cv2.imwrite(img_save_path, face_resize) # print('Processing %d / %d' % (frame_count, ftotal)) cap.release() print('Total face img: {}'.format(total_face))