You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在OpenCV中为HoughLinesP指定特定检测区域?

实现HoughLines仅在视频指定区域检测并显示

核心思路

通过创建**区域掩码(Mask)**过滤非目标区域的边缘信息,让Hough变换只处理指定区域内的边缘,最终仅在该区域显示检测到的直线。

具体步骤

  • 定义感兴趣区域(ROI):根据视频画面尺寸设置目标区域坐标(支持矩形或自定义多边形)
  • 生成掩码:创建与帧尺寸一致的全黑图像,将ROI区域填充为白色
  • 过滤边缘图:将Canny输出的边缘图与掩码做按位与操作,仅保留ROI内的边缘
  • 执行Hough检测:基于过滤后的边缘图运行HoughLinesP,确保检测结果仅来自目标区域

修改后的完整代码

import cv2
import numpy as np
import window_names
import track_bars

frame_counter = 0

vid = 'rain.mkv'

cap = cv2.VideoCapture(vid)

# 定义感兴趣区域(ROI),根据实际画面调整坐标
# 示例:取画面下半部分,(x_start, y_start) 到 (x_end, y_end)
frame_width = int(cap.get(cv2.CAP_PROP_FRAME_WIDTH))
frame_height = int(cap.get(cv2.CAP_PROP_FRAME_HEIGHT))
roi_x1, roi_y1 = 0, int(frame_height * 0.5)
roi_x2, roi_y2 = frame_width, frame_height

while (True):
    ret, frame = cap.read()
    if not ret:
        break

    frame_counter += 1
    if frame_counter == cap.get(cv2.CAP_PROP_FRAME_COUNT):
        frame_counter = 0
        cap.set(cv2.CAP_PROP_POS_FRAMES, 0)

    grey = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
    output = np.empty(grey.shape, dtype=np.uint8)
    cv2.normalize(grey, output, alpha=0, beta=255, norm_type=cv2.NORM_MINMAX)
    hist = cv2.equalizeHist(output)

    track_bars.lower_threshold = cv2.getTrackbarPos("lower", window_names.window_canny)
    track_bars.upper_threshold = cv2.getTrackbarPos("upper", window_names.window_canny)
    track_bars.smoothing_neighbourhood = cv2.getTrackbarPos("smoothing", window_names.window_canny)
    track_bars.sobel_size = cv2.getTrackbarPos("sobel size", window_names.window_canny)

    track_bars.smoothing_neighbourhood = max(3, track_bars.smoothing_neighbourhood)
    if not (track_bars.smoothing_neighbourhood % 2):
        track_bars.smoothing_neighbourhood += 1

    track_bars.sobel_size = max(3, track_bars.sobel_size)
    if not (track_bars.sobel_size % 2):
        track_bars.sobel_size += 1

    smoothed = cv2.GaussianBlur(hist, (track_bars.smoothing_neighbourhood, track_bars.smoothing_neighbourhood), 0)
    edges = cv2.Canny(smoothed, track_bars.lower_threshold, track_bars.upper_threshold, apertureSize=track_bars.sobel_size)

    # 创建掩码并过滤边缘图
    mask = np.zeros_like(edges)
    cv2.rectangle(mask, (roi_x1, roi_y1), (roi_x2, roi_y2), 255, thickness=cv2.FILLED)
    masked_edges = cv2.bitwise_and(edges, mask)

    rho = 1
    theta = np.pi / 180
    threshold = 15
    min_line_length = 50
    max_line_gap = 20
    line_image = np.copy(frame) * 0

    # 使用过滤后的边缘图执行Hough检测
    lines = cv2.HoughLinesP(masked_edges, rho, theta, threshold, np.array([]), min_line_length, max_line_gap)

    if lines is not None:
        for line in lines:
            x1, y1, x2, y2 = line[0]
            cv2.line(frame, (x1, y1), (x2, y2), (255, 0, 0), 5)

    lines_edges = cv2.addWeighted(frame, 0.8, line_image, 1, 0)

    cv2.imshow(window_names.window_hough, frame)
    cv2.imshow(window_names.window_canny, masked_edges)  # 可选:显示过滤后的边缘图

    key = cv2.waitKey(27)
    if key == ord('x'):
        break

cap.release()
cv2.destroyAllWindows()

关键说明

  • ROI自定义:可修改roi_x1, roi_y1, roi_x2, roi_y2调整目标区域;若需多边形区域,用cv2.fillPoly()替代cv2.rectangle()绘制掩码即可
  • 掩码作用:从根源上屏蔽非目标区域的边缘,确保Hough变换只处理指定区域的内容
  • 调试优化:代码中将显示的边缘图替换为masked_edges,可直观查看过滤效果,无需时改回edges即可

内容的提问来源于stack exchange,提问作者Isaac_E

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.31 21:25:22