How to extract relevant features to detect object?

asked 2016-07-12 04:25:09 -0600

astronaut gravatar image

updated 2016-07-12 04:41:29 -0600

Hi

I would like to detect the object (airplane door) from short distance. The algorithm should be very robust so can be implemented by any plane (with lots of different paintings, logos ) and by any weather condition(sun, rain, day and night).

I find algorithm that use SURF feature algorithms , so that find keypoints in two images (from file "scene" and "object" image) and calculate their descriptors. And the descriptors are the ones which we will compare to each other and determine whether the object was found in the scene or not. I would like to improve the algorithm’s robustness with respect to the correct matching of features. So, more reliable feature matching for the purpose of object recognition and detection to be more robust and reliable. Like for example, can include the distance between the window and door frame (which in every airplane model is fix), then the thickness of the door frame etc.

Any Help?

Here the label, label2, matches and the match images.

label

label2

matches

match

Here is the code

#include <opencv2\core\core.hpp>
#include <opencv2\highgui\highgui.hpp>
#include <opencv2\features2d\features2d.hpp>
#include <opencv2\nonfree\features2d.hpp>
#include <opencv2\objdetect\objdetect.hpp>
#include <opencv2\calib3d\calib3d.hpp>
#include <iostream>

using namespace cv;
using namespace std;

    //read an image 
    Mat sceneP = imread("image_scene.jpg"); 
    Mat outImg;

void findObject ( Mat objectP, int minHessian, Scalar color );

int main() {

    Mat find = imread("image_object.jpg");  
    Mat label = imread("label2_door.jpg");
    Mat label2 = imread("label1_door.jpg");
    outImg = sceneP;


    if(find.empty() && sceneP.empty())
    {
        cout << "Could not load the image!" << endl;        
        exit(0);
    }
    else
    {
        cout << "Images loaded succesfully" << endl;
    }

    findObject( label, 2500, Scalar(255,0,0) );
    findObject( label2, 1500, Scalar(0,255,0) );
    findObject ( find, 1500, Scalar(0,0,255) );         

    namedWindow("Match");
    imshow("Match",outImg);
    waitKey(0);
    return 1;
}

void findObject( Mat objectP, int minHessian, Scalar color )
{
    //vector of keypoints   
    vector<cv::KeyPoint> keypointsO;
    vector<cv::KeyPoint> keypointsS;
    cout << "Looking for object...\n";
    //Start the timer
    double duration;
    duration = static_cast<double>(cv::getTickCount());

    SurfFeatureDetector surf(1500);
    surf.detect(objectP,keypointsO);
    surf.detect(sceneP,keypointsS);

    //-- Step 2: Calculate descriptors (feature vectors)
  SurfDescriptorExtractor extractor;

  Mat descriptors_object, descriptors_scene;

  extractor.compute( objectP, keypointsO, descriptors_object );
  extractor.compute( sceneP, keypointsS, descriptors_scene );

  //-- Step 3: Matching descriptor vectors using FLANN matcher
  FlannBasedMatcher matcher;  
  //BFMatcher matcher(NORM_L1);
  std::vector< DMatch > matches;
  matcher.match( descriptors_object, descriptors_scene, matches );

  double max_dist = 0; double min_dist = 150;
  double dist;

  //Quick calculation of min and max distances between keypoints
  for(int i=0; i<descriptors_object.rows; i++)
  {
    dist = matches[i].distance;
    if( dist < min_dist ) min_dist = dist;
    if( dist > max_dist ) max_dist = dist;
  }

 /* cout << "-- Max Dist: " << max_dist << endl;
  cout << "-- Min Dist: " << min_dist << endl;*/

  vector< DMatch > good_matches;

  for(int i = 0; i < descriptors_object.rows; i++)
  {
      if( matches[i].distance < 3*min_dist) 
          good_matches.push_back( matches[i] );
  }

    //drawMatches(objectP,keypointsO,sceneP,keypointsS,matches,outImg,Scalar::all(-1), Scalar::all(-1),vector<char>(),DrawMatchesFlags::NOT_DRAW_SINGLE_POINTS);

    /*drawKeypoints(objectP,keypointsO,objectP,Scalar(0,0,255),DrawMatchesFlags::DRAW_RICH_KEYPOINTS);

    namedWindow("SURF");
    imshow("SURF",objectP);*/

    //-- Localize the object

  if( good_matches.size() >=8 && good_matches.size() <= 30)
  {
    cout << "OBJECT FOUND!" << endl ...
(more)
edit retag flag offensive close merge delete

Comments

"so can be implemented by any plane (with lots of different paintings, logos)"

that's a broken assumption. different logos will result in different keypoints / features. imho, you have to re-think your whole approach.

berak gravatar imageberak ( 2016-07-13 00:47:51 -0600 )edit

No. Its not like that. I wonted to say that should work for any planes with any paintings and logos.Means the algorithm should be robust to detect the door by any type of plane.Logos are not keypoints/features.

So because of that I like to extract features that can be general like distance between the window and the door frame(as this feature is always the same for given airplane model). Like for example the minimal distance between the door frame and the nearest window in Airbus A350 is let we say 1m. So I would like to use this feature in my algorithm. Understand? Or should post a new question regarding extracting a specific feature like that distance?

astronaut gravatar imageastronaut ( 2016-07-13 01:05:54 -0600 )edit