c - 在 OpenCV 中使用直方图数据跟踪对象

标签 c visual-studio-2010 image-processing opencv histogram

我正在尝试使用对象的直方图数据来跟踪图像内的对象。我传入引用图像来获取直方图数据并将其存储在 Mat 中。从那里我加载图像并尝试使用直方图数据来检测对象。我遇到的问题不仅是它没有跟踪对象,而且没有更新检测。如果我加载图像“1.jpg”,检测将声称该对象位于右上角,而实际上它位于左下角。当我传递第二张图像时,检测区域根本没有移动。这也适用于下一批图像。下面是我的应用程序的代码片段。

这是在 Windows 7 32 位环境中使用 VS2010 中的 OpenCV2.3 完成的。预先感谢您的帮助

int main( int argc, char** argv )
{
    vector<string> szFileNames;
    IplImage* Image;
    Mat img, hist, backproj;
    Rect trackWindow;

    // Load histogram data
    hist = ImageHistogram("C:/Users/seb/Documents/redbox1.jpg", backproj);

    Image = cvLoadImage("C:/Users/seb/Documents/1.jpg");
        img = Mat(Image);
    trackWindow = Rect(0, 0, Image->width, Image->height);

    imshow("Histogram", hist);

    while(true)
    {
        Detection(img, backproj, trackWindow);
        imshow("Image", img);

        char c = cvWaitKey(1);

        switch(c)
        {
            case 32:
            {
                cvReleaseImage(&Image);
                Image = cvLoadImage("C:/Users/seb/Documents/redbox2.jpg");
                img = Mat(Image);
                break;
            }
        }
    }

    cvReleaseImage(&Image);

    // Destroy all windows
    cvDestroyWindow("Histogram");
    cvDestroyWindow("Image");

    return 0;
}

Mat ImageHistogram(string szFilename, Mat& backproj)
{
    // Create histogram values
    int vmin = 10;
    int vmax = 256;
    int smin = 30;
    int hsize = 16;
    float hranges[] = {0,180};
    const float* phranges = hranges;

    // Load the image
    IplImage* Image = cvLoadImage(szFilename.c_str());
    Rect rect = Rect(0, 0, Image->width, Image->height);

    // Convert Image to a matrix
    Mat ImageMat = Mat(Image);

    // Create and initialize the Histogram
    Mat hsv, mask, hue, hist, histimg = Mat::zeros(200, 320, CV_8UC3);
    cvtColor(ImageMat, hsv, CV_BGR2HSV);

    // Create and adjust the histogram values
    inRange(hsv, Scalar(0, smin, vmin), Scalar(180, 256, vmax), mask);
    int ch[] = {0, 0};

    hue.create(hsv.size(), hsv.depth());
    mixChannels(&hsv, 1, &hue, 1, ch, 1);

    Mat roi(hue, rect), maskroi(mask, rect);
    calcHist(&roi, 1, 0, maskroi, hist, 1, &hsize, &phranges);
    normalize(hist, hist, 0, 255, CV_MINMAX);

    histimg = Scalar::all(0);
    int binW = histimg.cols / hsize;
    Mat buf(1, hsize, CV_8UC3);
    for( int i = 0; i < hsize; i++ )
        buf.at<Vec3b>(i) = Vec3b(saturate_cast<uchar>(i*180./hsize), 255, 255);
    cvtColor(buf, buf, CV_HSV2BGR);

    for( int i = 0; i < hsize; i++ )
    {
        int val = saturate_cast<int>(hist.at<float>(i)*histimg.rows/255);
        rectangle( histimg, Point(i*binW,histimg.rows),
            Point((i+1)*binW,histimg.rows - val),
            Scalar(buf.at<Vec3b>(i)), -1, 8 );
    }

    calcBackProject(&hue, 1, 0, hist, backproj, &phranges);
    backproj &= mask;

    cvReleaseImage(&Image);

    return histimg;
}

void Detection(Mat& image, Mat& backproj, Rect& trackWindow)
{
    RotatedRect trackBox = CamShift(backproj, trackWindow, TermCriteria( CV_TERMCRIT_EPS | CV_TERMCRIT_ITER, 10, 1 ));
    int test2 = trackWindow.area();
    if(trackBox.size.height > 0 && trackBox.size.width > 0)
    {
        if( trackWindow.area() <= 1 )
        {
            int cols = backproj.cols, rows = backproj.rows, r = (MIN(cols, rows) + 5)/6;
            trackWindow = Rect(trackWindow.x - r, trackWindow.y - r,
                trackWindow.x + r, trackWindow.y + r) &
                Rect(0, 0, cols, rows);
        }

        int test = trackBox.size.area();
        if(test >= 1)
        {
            rectangle(image, trackBox.boundingRect(), Scalar(255,0,0), 3, CV_AA);
            ellipse( image, trackBox, Scalar(0,0,255), 3, CV_AA );
        }
    }
}

最佳答案

我已经解决这个问题了。它必须处理我不转换我正在检查的图像的问题。我必须从彩色框中获取直方图数据,然后我必须从用于搜索的图像中获取直方图。

关于c - 在 OpenCV 中使用直方图数据跟踪对象,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6666409/

相关文章:

visual-studio-2010 - C++/CLI 混合模式调试挂起(经常)

c++ - C++ 中的模式识别

c - 使用 scanf 获取小数

c - 填写C语言程序

c - 递归添加数字序列

c++ - 为什么指向未定义结构的指针有时在 C 和 C++ 中是非法的

.net - 如何将用户控件添加到 Visual Studio 2010 中的 Windows 窗体应用程序?

visual-studio-2010 - 如何在 Visual Studio 2010 中精确计时测试运行

iphone - GPUImage:混合两个图像

c - 延迟/保留 opencv 连续帧中的文本