diff --git a/doco/src/doco/video_split.py b/doco/src/doco/video_split.py index ede3b3a..de95c0e 100644 --- a/doco/src/doco/video_split.py +++ b/doco/src/doco/video_split.py @@ -46,8 +46,10 @@ SUBTITLE_CROP = "iw:ih*0.2:0:ih*0.8" # ======================================================================== # 空白帧检测(黑底白字场景专用) -# 亮度阈值:0-255,>200 视为接近白色像素 -BLANK_FRAME_BRIGHTNESS_THRESHOLD = 200 +# 亮度阈值:0-255,>=240 视为接近纯白的"白像素" +# 从 200 提到 240(2026-06-12):过滤视频压缩产生的灰白噪点(亮度 200-230), +# 同时保留真实字幕白字(亮度接近 255) +BLANK_FRAME_BRIGHTNESS_THRESHOLD = 240 # 白色像素占比阈值:< 0.5% 则判定为空白帧(留气口黑画面) BLANK_FRAME_WHITE_PIXEL_RATIO = 0.005 @@ -194,7 +196,8 @@ def is_blank_frame(image_path: Path, debug: bool = False) -> Tuple[bool, float]: frame_idx = image_path.stem print(f"[debug] {frame_idx}, white_ratio={white_ratio:.6f}, is_blank={is_blank}") - return is_blank, white_ratio + max_brightness = int(np.max(arr)) + return is_blank, white_ratio, max_brightness # ======================================================================== @@ -284,14 +287,14 @@ def find_keyframes( csv_writer = csv.writer(csv_file) csv_writer.writerow([ "frame_index", "timestamp_ms", "white_pixel_ratio", "is_blank", - "hash_value", "iou_to_prev", "hash_dist_to_prev", + "max_brightness", "hash_value", "iou_to_prev", "hash_dist_to_prev", "decision", "keyframe_index" ]) threshold = phash_threshold if hash_algorithm == "phash" else dhash_threshold for frame_index, timestamp_ms, image_path in frames: - is_blank, white_ratio = is_blank_frame(image_path, debug=False) + is_blank, white_ratio, max_brightness = is_blank_frame(image_path, debug=False) hash_value = compute_hash(image_path, hash_algorithm) decision = "kept" @@ -358,6 +361,7 @@ def find_keyframes( timestamp_ms, f"{white_ratio:.6f}", is_blank, + max_brightness, hash_value, f"{iou_to_prev:.6f}" if iou_to_prev is not None else "", hash_dist_to_prev if hash_dist_to_prev is not None else "", @@ -522,7 +526,7 @@ def split_video( decision_stats = {"blank": 0, "duplicate(iou)": 0, "duplicate(hash)": 0, "keyframe(hash)": 0, "kept": 0} for frame_index, timestamp_ms, image_path in frames: - is_blank, white_ratio = is_blank_frame(image_path, debug=False) + is_blank, white_ratio, max_brightness = is_blank_frame(image_path, debug=False) if is_blank: blank_count += 1 decision_stats["blank"] += 1