Meanshift's object tracking algorithm generates a centroid update to the search box

I am trying to implement a tool change algorithm for tracking objects and have reviewed related concepts.

Now I was able to successfully generate the reverse stream from my camera using the hue roi single-channel histogram and a single-channel video stream that seems great, I know that there is a return function in the opencv library, but I'm trying to implement it myself using data structures, presented in opencv, calculating the moments and calculating the average centroid of the search box.

But for some reason I cannot find the problem in my code, as it continues to converge in the upper left corner of my video stream for any input roi (region of interest) that needs to be tracked. The following is a snippet of the function code for calculating the center of gravity of the search box, where I feel the problem lies, but not sure what it is, I would really appreciate it if someone could point me in the right direction:

void moment(Mat &backproj, Rect &win){

    int x_c, y_c, x_c_new, y_c_new;    
    int idx_row, idx_col;
    double m00 = 0.0 , m01 = 0.0 , m10 = 0.0 ;
    double res = 1.0, TOL = 0.003 ;

    //Set the center of search window as the center of the probabilistic image:
    y_c =  (int) backproj.rows / 2 ; 
    x_c =  (int) backproj.cols / 2 ; 

    //Centroid search solver until residual below certain tolerance:
    while (res > TOL){

        win.width = (int) 80; 
        win.height = (int) 60; 

        //First array element at position (x,y) "lower left corner" of the search window:
        win.x = (int) (x_c - win.width / 2) ;
        win.y = (int) (y_c - win.height / 2); 

        //Modulo correction since modulo of negative integer is negative in C:
        if (win.x < 0)
                win.x = win.x % backproj.cols + backproj.cols ;

        if (win.y < 0)
                win.y = win.y % backproj.rows + backproj.rows ;   

        for (int i = 0; i < win.height; i++ ){  

                //Traverse along y-axis (height) i.e. rows ensuring wrap around top/bottom boundaries:                  
                idx_row = (win.y + i) % (int)backproj.rows ;

                for (int j = 0; j < win.width; j++ ){

                        //Traverse along x-axis (width) i.e. cols ensuring wrap around left/right boundaries:
                        idx_col = (win.x + j) % (int)backproj.cols ;    
                        //Compute Moments:                            
                        m00 += (double) backproj.at<uchar>(idx_row, idx_col) ;
                        m10 += (double) backproj.at<uchar>(idx_row, idx_col) * i ;
                        m01 += (double) backproj.at<uchar>(idx_row, idx_col) * j ;
                }
        }

        //Compute new centroid coordinates of the search window:
        x_c_new = (int) ( m10 / m00 ) ;
        y_c_new = (int) ( m01 / m00 );

        //Compute the residual:
        res = sqrt( pow((x_c_new - x_c), 2.0) + pow((y_c_new - y_c), 2.0) ) ;

        //Set new search window centroid coordinates:
        x_c = x_c_new;
        y_c = y_c_new;
    }
}

This is my second stackoverflow request, so please excuse me for any recommendations I forgot to follow.

EDIT

modified m00, m01, m10 to block level variables inside WHILE-LOOP instead of function level variables, thanks to Daniel Strul, specifying it, but the problem still remains. Now the search box jumps around the borders of the frame, and does not focus on roi.

    void moment(Mat &backproj, Rect &win){

    int x_c, y_c, x_c_new, y_c_new;    
    int idx_row, idx_col;
    double m00 , m01 , m10 ;
    double res = 1.0, TOL = 0.003 ;

    //Set the center of search window as the center of the probabilistic image:
    y_c =  (int) backproj.rows / 2 ; 
    x_c =  (int) backproj.cols / 2 ; 

    //Centroid search solver until residual below certain tolerance:
    while (res > TOL){

        m00 = 0.0 , m01 = 0.0 , m10 = 0.0
        win.width = (int) 80; 
        win.height = (int) 60; 

        //First array element at position (x,y) "lower left corner" of the search window:
        win.x = (int) (x_c - win.width / 2) ;
        win.y = (int) (y_c - win.height / 2); 

        //Modulo correction since modulo of negative integer is negative in C:
        if (win.x < 0)
                win.x = win.x % backproj.cols + backproj.cols ;

        if (win.y < 0)
                win.y = win.y % backproj.rows + backproj.rows ;   

        for (int i = 0; i < win.height; i++ ){  

                //Traverse along y-axis (height) i.e. rows ensuring wrap around top/bottom boundaries:                  
                idx_row = (win.y + i) % (int)backproj.rows ;

                for (int j = 0; j < win.width; j++ ){

                        //Traverse along x-axis (width) i.e. cols ensuring wrap around left/right boundaries:
                        idx_col = (win.x + j) % (int)backproj.cols ;    
                        //Compute Moments:                            
                        m00 += (double) backproj.at<uchar>(idx_row, idx_col) ;
                        m10 += (double) backproj.at<uchar>(idx_row, idx_col) * i ;
                        m01 += (double) backproj.at<uchar>(idx_row, idx_col) * j ;
                }
        }

        //Compute new centroid coordinates of the search window:
        x_c_new = (int) ( m10 / m00 ) ;
        y_c_new = (int) ( m01 / m00 );

        //Compute the residual:
        res = sqrt( pow((x_c_new - x_c), 2.0) + pow((y_c_new - y_c), 2.0) ) ;

        //Set new search window centroid coordinates:
        x_c = x_c_new;
        y_c = y_c_new;
    }
}
+4
1

, , , m00, m10 m01 reset :

  • 0 m00, m10 m01 m 0
  • 0 1 reset
  • , 1 m00, m10 m01 (m 0 + m 1)
  • 2 (m 0 + m 1 + m 2)
  • , .

, reset .

, , ( ):

while (res > TOL){
    ...
    double m00 = 0.0, m01 = 0.0, m10 = 0.0;
    for (int i = 0; i < win.height; i++ ){
        ...

1

, (ROI, ), , i j.

, [avg (j), avg (i)], [avg (y), avg (x)]. , . .

2 - ROI :

    x_c_new = win.x + (int) ( m10 / m00 ) ;
    y_c_new = win.y + (int) ( m01 / m00 );
+1

Source: https://habr.com/ru/post/1613255/


All Articles