【问题标题】:How to use the CSRT Tracker correctly to track objects in OpenCV如何正确使用 CSRT Tracker 来跟踪 OpenCV 中的对象
【发布时间】:2021-01-02 23:46:56
【问题描述】:

我尝试使用来自 OpenCv V4.5.1CSRT 跟踪器来跟踪视频序列中的人脸,在 一些 视频的结尾我收到了这个错误,我不明白为什么会这样它发生了!

  • 我正在使用AVDIAR dataset
  • 能否请您告诉我如何正确使用跟踪器和 Viola-Jones 人脸检测器?

注意:我使用KCF Tracker 的东西运行良好! tracker = cv2.TrackerKCF_create()

---> 12     tracker.init(frame, myBox)
error: OpenCV(4.5.1) C:\Users\appveyor\AppData\Local\Temp\1\pip-req-build-r2ue8w6k\opencv\modules\core\src\matrix.cpp:811:
error: (-215:Assertion failed) 
0 <= roi.x && 0 <= roi.width && roi.x + roi.width <= m.cols && 0 <= roi.y && 0 <= roi.height && roi.y + roi.height <= m.rows 
in function 'cv::Mat::Mat'

我用来使用跟踪器的代码是:

def tracking(frame, bbox):
    """
    Parameters:
    @param: frame: nd-array frame from video sequence.
    @param: bbox: bounding box
    """
    [x0, y0, x1, y1] = bbox
    myBox = (x0, y0, x1, y1)
    tracker = cv2.TrackerCSRT_create()

    # Initialize tracker with first frame and bounding box
    tracker.init(frame, myBox)
    # Update tracker
    ok, box = tracker.update(frame)
    if ok:
        [x0, x1] = [x0, x1] if x1>x0 else [x1, x0]
        [y0, y1] = [y0, y1] if y1>y0 else [y1, y0]
        result = [x0, y0, x1, y1]
        return result
    print("tracking No result ", bbox)
    return bbox

调用跟踪的函数是:

def violaJones(xmlPath, videoPath, verbose=False):
    """
    Parameters:
    @param: xmlPath: string, path to the Haar_Cascade xml file.
    @param: videoPath: string, Video Full Path.
    @param: verbose
    """
    # print(videoPath)
    cap = cv2.VideoCapture(videoPath)
    bboxes = {}
    nb_frame = 0
    # Blue color in BGR 
    color = [(255, 128, 128),(128, 255, 128),(128, 128, 255), (128,255,255),(255,128,255), (255,255,128)]
    # Line thickness of 2 px 
    thickness = 2
    # max numer of people
    maxID = 0
    track = [None]*10
    # Read until video is completed
    while (cap.isOpened()):
        
        # Capture frame-by-frame
        ret, frame = cap.read()
        if ret:
            # 
            gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
            gauss = cv2.GaussianBlur(gray, (3, 3), 0)
            # gauss = skinThresh(frame)
            # Cascade Classifier
            face_cascade = cv2.CascadeClassifier(xmlPath)
            detected_faces = face_cascade.detectMultiScale(gauss.astype(np.uint8), 1.2, 4)
            id = 0
            for (x0,y0,w,h) in detected_faces:
                id += 1
                maxID = maxID if maxID > id else id
                x1 = x0 + w
                y1 = y0 + h
                # Tracking
                track[id-1] = tracking(frame, [x0, y0, x1, y1])

            for ID in range(maxID):
                if track[ID] is not None:
                    bboxes[str(nb_frame)+str(ID+1)] = np.array(tracking(frame, track[ID]))
                    # Draw Annotations
                    if verbose:
                        [xx0, yy0, xx1, yy1] = track[ID]
                        cv2.rectangle(frame, (xx0,yy0),(xx1,yy1), color[ID], thickness)
            # show
            if verbose:
                cv2.imshow("Viola_Jones", frame)
                key = cv2.waitKey(1) & 0xFF
        # Break the loop
        else:
            break
        nb_frame +=1
    # Closes all the frames
    cv2.destroyAllWindows()
    # When everything done, release the video capture object
    cap.release()
    return bboxes

打印函数出错前的最后一个值是:

x0 y0 x1 y1 Frame Shape
574 46 634 106 (450, 720, 3)
600 35 663 98 (450, 720, 3)
600 35 663 98 (450, 720, 3)
600 35 663 98 (450, 720, 3)
600 35 663 98

【问题讨论】:

  • 显示其余代码。 frame 可能是空的,因为大家都用错了 VideoCapture。
  • @ChristophRackwitz 添加了其余代码。
  • 这段代码有太多问题了。您为每一帧重新实例化跟踪器实例。您应该这样做一次并保留跟踪器实例。

标签: python opencv computer-vision tracking


【解决方案1】:

解决方案是为每个对象声明一个跟踪器,并启动该跟踪器一次,如下所示:

追踪功能

def tracking(frame, bbox, tracker, Init):
    """
    Parameters:
    @param: frame: nd-array frame from video sequence.
    @param: bbox: bounding box
    @param: tracker: tracker from OpenCV such as KCF or CSRT
    """
    [x0, y0, x1, y1] = bbox
    myBox = (x0, y0, x1, y1)
    if(not Init):
        # Initialize tracker with first frame and bounding box
        tracker.init(frame, myBox)
        Init = True
    # Update tracker
    ok, box = tracker.update(frame)
    if ok:
        [x0, x1] = [x0, x1] if x1>x0 else [x1, x0]
        [y0, y1] = [y0, y1] if y1>y0 else [y1, y0]
        result = [x0, y0, x1, y1]
        return result
    return bbox

维奥拉-琼斯

def violaJones(xmlPath, videoPath, verbose=False):
    """
    Parameters:
    @param: xmlPath: string, path to the Haar_Cascade xml file.
    @param: videoPath: string, Video Full Path.
    @param: verbose, bolean to visualize the results.
    """
    # print(videoPath)
    cap = cv2.VideoCapture(videoPath)
    bboxes = {}
    nb_frame = 0
    # Blue color in BGR 
    color = [(255, 128, 128),(128, 255, 128),(128, 128, 255), (128,255,255),(255,128,255), (255,255,128)]
    # Line thickness of 2 px 
    thickness = 2
    # max numer of people
    maxID = 0
    track = [None]*10

    trackInit = [False]*5

    tracker1 = cv2.TrackerKCF_create()
    tracker2 = cv2.TrackerKCF_create()
    tracker3 = cv2.TrackerKCF_create()
    tracker4 = cv2.TrackerKCF_create()
    tracker5 = cv2.TrackerKCF_create()

    trackers = [tracker1, tracker2, tracker3, tracker4, tracker5]
    # tracker1 = cv2.TrackerCSRT_create()
    # tracker2 = cv2.TrackerKCF_create()

    # Read until video is completed
    while (cap.isOpened()):
        
        # Capture frame-by-frame
        ret, frame = cap.read()
        if ret:
            # 
            # gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
            # gauss = cv2.GaussianBlur(gray, (3, 3), 0)
            gauss = skinThresh(frame)
            # Cascade Classifier
            face_cascade = cv2.CascadeClassifier(xmlPath)
            detected_faces = face_cascade.detectMultiScale(gauss, 1.2, 4)
            id = 0
            for (x0,y0,w,h) in detected_faces:
                id += 1
                maxID = maxID if maxID > id else id
                x1 = x0 + w
                y1 = y0 + h
                # Detection
                track[id-1] = [x0, y0, x1, y1]

            for ID in range(maxID):
                #Tracking
                if track[ID] is not None:
                    bboxes[str(nb_frame)+str(ID+1)] = np.array(tracking(frame, track[ID], trackers[ID], trackInit[ID]))
                    trackInit[ID] = True
                    # Draw Annotations
                    if verbose:
                        [xx0, yy0, xx1, yy1] = track[ID]
                        cv2.rectangle(frame, (xx0,yy0),(xx1,yy1), color[ID], thickness)
            # show
            if verbose:
                cv2.imshow("Viola_Jones", frame)
                key = cv2.waitKey(1) & 0xFF
        # Break the loop
        else:
            break
        nb_frame +=1
    # When everything done, release the video capture object
    cap.release()
    # Closes all the frames
    cv2.destroyAllWindows()
    return bboxes

【讨论】:

  • 我想你只考虑固定数量的面孔,没有新面孔或旧面孔消失?否则ID会失败对吗?另外,这段代码中没有数据关联对吧(如果我错了,请启发我......)?
  • @dexter2406 修复了最大个人脸,ID和人脸的映射仍然存在一些严重的问题。
猜你喜欢
  • 2012-11-17
  • 1970-01-01
  • 2014-01-09
  • 2019-12-07
  • 2017-04-25
  • 1970-01-01
  • 1970-01-01
  • 2021-07-28
  • 2017-03-21
相关资源
最近更新 更多