ALL UNANSWERED FOLLOWED Ask Your Question 0 How to detect the shape of an object whilst the object is moving?

I have wrote the following shape code, but i'm having some difficulties regarding how it works. I want to be able to track the shape of the object whilst the object is moving, but at the moment the code below only tracks the shape of the object whilst the object is standstill and why whilst it is moving very slowly. Anyone knows any modifications i can make to the code to make it track objects moving quite fast? Thanks very much in advance.

/**
* Simple shape detector program.
* It loads an image and tries to find simple shapes (rectangle, triangle, circle, etc) in it.
* This program is a modified version of `squares.cpp` found in the OpenCV sample dir.
*/
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>
#include <cmath>
#include <iostream>
#include <sstream>
#include <string>
#include <iostream>
#include <opencv/highgui.h>
#include <opencv/cv.h>
#include <opencv2/imgproc/imgproc.hpp>
#include <fcntl.h>
#include <stdio.h>
#include <unistd.h>

/**
* Helper function to find a cosine of angle between vectors
* from pt0->pt1 and pt0->pt2
*/
cv::Mat dst2;


static double angle(cv::Point pt1, cv::Point pt2, cv::Point pt0)
{
double dx1 = pt1.x - pt0.x;
double dy1 = pt1.y - pt0.y;
double dx2 = pt2.x - pt0.x;
double dy2 = pt2.y - pt0.y;
return (dx1*dx2 + dy1*dy2)/sqrt((dx1*dx1 + dy1*dy1)*(dx2*dx2 + dy2*dy2) + 1e-10);

}

/**
* Helper function to display text in the center of a contour
*/
void setLabel(cv::Mat& im, const std::string label, std::vector<cv::Point>& contour)
{
int fontface = cv::FONT_HERSHEY_SIMPLEX;
double scale = 0.4;
int thickness = 1;
int baseline = 0;


cv::Size text = cv::getTextSize(label, fontface, scale, thickness, &baseline);
cv::Rect r = cv::boundingRect(contour);

cv::Point pt(r.x + ((r.width - text.width) / 2), r.y + ((r.height + text.height) / 2));
cv::rectangle(im, pt + cv::Point(0, baseline), pt + cv::Point(text.width, -text.height), CV_RGB(255,255,255), CV_FILLED);
cv::putText(im, label, pt, fontface, scale, CV_RGB(0,0,0), thickness, 8);
}

int main()
{
//cvNamedWindow("Camera_Output", 1); //Create window
CvCapture* capture = cvCaptureFromCAM(1); //Capture using any camera connected to your system

while(1){
IplImage * img = cvQueryFrame(capture);
cvSmooth(img, img, CV_GAUSSIAN,3,3);

//show the original image
//cvNamedWindow("Raw");
//cvShowImage("Raw",img);


cv::Mat src(img);

//cv::Mat src = cv::imread("/home/john/Desktop/basic-shapes.png");
//if (src.empty())
//return -1;

// Convert to grayscale
cv::Mat gray;
cv::cvtColor(src, gray, CV_BGR2GRAY);

// Use Canny instead of threshold to catch squares with gradient shading
cv::Mat bw;
cv::Canny(gray, bw, 0, 50, 5);

// Find contours
std::vector<std::vector<cv::Point> > contours;
cv::findContours(bw.clone(), contours, CV_RETR_EXTERNAL, CV_CHAIN_APPROX_SIMPLE);

std::vector<cv::Point> approx;
cv::Mat dst = src.clone();


for (int i = 0; i < contours.size(); i++)
{
// Approximate contour with accuracy proportional
// to the contour perimeter
cv::approxPolyDP(cv::Mat(contours[i]), approx, cv::arcLength(cv::Mat(contours[i]), true)*0.04, true);

// Skip small or non-convex objects
if (std::fabs(cv::contourArea(contours[i])) < 500 || !cv::isContourConvex(approx))
continue;

if (approx.size() == 3)
{

//setLabel(dst, "TRI", contours[i]); // Triangles
}

else if (approx.size() >= 4 && approx.size() <= 6)
{
// Number of vertices of polygonal curve
int vtc = approx.size();

// Get the cosines of all corners
std::vector<double> cos;
for (int j = 2; j < vtc+1; j++)
cos.push_back(angle(approx[j%vtc], approx[j-2], approx[j-1]));

// Sort ascending the cosine values
std::sort(cos.begin(), cos.end());

// Get the lowest and the highest cosine
double mincos = cos.front();
double maxcos = cos.back();

// Use the degrees obtained above and the number of vertices
// to determine the shape of the contour
if (vtc == 4 && mincos >= -0.1 && maxcos <= 0.3)
{
// Detect rectangle or square
cv::Rect r = cv::boundingRect(contours[i]);
double ratio = std::abs(1 - (double)r.width / r.height);
setLabel(dst, ratio <= 0.02 ? "SQU" : "RECT", contours[i]);
}
//else if (vtc == 4 && mincos >= -0.1 && maxcos <= 0.3)
//setLabel(dst, "RECT", contours[i]);
else if (vtc == 5 && mincos >= -0.34 && maxcos <= -0.27)
setLabel(dst, "PENTA", contours[i]);
else if (vtc == 6 && mincos >= -0.55 && maxcos <= -0.45)
setLabel(dst, "HEXA", contours[i]);
}
else
{
// Detect and label circles
double area = cv::contourArea(contours[i]);
cv::Rect r = cv::boundingRect(contours[i]);
int radius = r.width / 2;

if (std::abs(1 - ((double)r.width / r.height)) <= 0.2 &&
std::abs(1 - (area / (CV_PI * std::pow(radius, 2)))) <= 0.2)
setLabel(dst, "CIR", contours[i]);
}
}


cv::imshow("dst", dst);
//cv::imshow("src", src);


cv::waitKey(10);
}

return 0;
}
Topic archived. No new replies allowed.