Guest User

Untitled

a guest
May 8th, 2012
98
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 4.41 KB | None | 0 0
  1. #include <opencv2/core/core.hpp>
  2. #include <opencv2/highgui/highgui.hpp>
  3. #include <iostream>
  4. #include <cmath>
  5.  
  6. #define PI 3.14159265
  7.  
  8. #define uchar unsigned char
  9.  
  10. using namespace std;
  11.  
  12. struct HoughLine
  13. {
  14.     double theta;
  15.     double r;
  16. };
  17.  
  18.  
  19.  
  20. int main( int argc, char** argv )
  21. {
  22.  
  23.     const int neighbourhoodSize = 4;
  24.     int maxTheta = 180;
  25.     double thetaStep = PI / maxTheta;
  26.     int ** houghArray;
  27.     float centerX, centerY;
  28.     int houghHeight;
  29.     int doubleHeight;
  30.     int numPoints;
  31.     double * sinCache;
  32.     double * cosCache;
  33.  
  34.     if(argc < 3)
  35.     {
  36.         cout << "Usage: " << argv[0] <<" imageName threashold" << endl;
  37.         return -1;
  38.     }
  39.  
  40.     cv::Mat img = cv::imread(argv[1], 0); //imagem original
  41.     cv::Mat linesImg;  // imagem linhas
  42.     cv::Mat houghImg;  // imagem espaço de hough
  43.  
  44.     int width = img.cols;
  45.     int height = img.rows;
  46.  
  47.     linesImg.create(height, width, CV_8UC1);
  48.     linesImg = 255;
  49.  
  50.  
  51.     houghHeight = (int)  (  sqrt(2.0) * std::max<int>(img.rows, img.cols));
  52.  
  53.     doubleHeight = 2 * houghHeight;
  54.  
  55.     houghArray = new int*[maxTheta];
  56.  
  57.     for(int i = 0 ; i<maxTheta; i++)
  58.     {
  59.         houghArray[i] = new int[doubleHeight];
  60.         memset(houghArray[i], 0, doubleHeight*sizeof(int));
  61.     }
  62.  
  63.     centerX = width / 2;
  64.     centerY = height / 2;
  65.  
  66.     numPoints = 0;
  67.  
  68.     sinCache = new double[maxTheta];
  69.     cosCache =  new double[maxTheta];
  70.  
  71.  
  72.     for (int t = 0; t < maxTheta; t++) {
  73.         double realTheta = t * thetaStep;
  74.         sinCache[t] = sin(realTheta);
  75.         cosCache[t] = cos(realTheta);
  76.     }
  77.  
  78.  
  79.     for(int i=0; i< img.rows; i++)
  80.     {
  81.         uchar * pixel = img.ptr<uchar>(i);
  82.  
  83.         for( int j=0; j<img.cols; j++)
  84.         {
  85.             if(pixel[j] < 100)
  86.             {
  87.                 int x = j;
  88.                 int y = img.rows - i;
  89.  
  90.                 for (int t = 0; t < maxTheta; t++) {
  91.                     int r = (int) (((x - centerX) * cosCache[t]) + ((y - centerY) * sinCache[t]));
  92.                     r += houghHeight;
  93.                     if (r < 0 || r >= doubleHeight) continue;
  94.  
  95.                     houghArray[t][r]++;
  96.  
  97.                 }
  98.                 numPoints++;
  99.             }
  100.         }
  101.     }
  102.  
  103.  
  104.     vector<HoughLine> lines;
  105.  
  106.     float threshold = 0;
  107.     sscanf(argv[2], "%f", &threshold);
  108.     int newr;
  109.     int r;
  110.     bool onLoop = false;
  111.  
  112.  
  113.     if (numPoints != 0)
  114.     {
  115.         for (int t = 0; t < maxTheta; t++)
  116.         {
  117. loop:
  118.             if(onLoop)
  119.             {
  120.                 newr = ++r;
  121.                 onLoop = false;
  122.             }
  123.             else newr = neighbourhoodSize;
  124.  
  125.             for (r = newr; r < doubleHeight - neighbourhoodSize; r++)
  126.             {
  127.                 if (houghArray[t][r] > threshold)
  128.                 {
  129.                     int peak = houghArray[t][r];
  130.  
  131.                     for (int dx = -neighbourhoodSize; dx <= neighbourhoodSize; dx++)
  132.                     {
  133.                         for (int dy = -neighbourhoodSize; dy <= neighbourhoodSize; dy++)
  134.                         {
  135.                             int dt = t + dx;
  136.                             int dr = r + dy;
  137.                             if (dt < 0) dt = dt + maxTheta;
  138.                             else if (dt >= maxTheta) dt = dt - maxTheta;
  139.                             if (houghArray[dt][dr] > peak) {
  140.                                 onLoop = true;
  141.                                 goto loop;
  142.                             }
  143.                         }
  144.                     }
  145.  
  146.                     double theta = t * thetaStep;
  147.  
  148.                     // add the line to the vector
  149.                     HoughLine l;
  150.                     l.r = r;
  151.                     l.theta = theta;
  152.                     lines.push_back(l);
  153.                 }
  154.             }
  155.         }
  156.     }
  157.  
  158.     cout << "Numero de linhas encontradas utilizando o threshold " << threshold << " : " <<lines.size() <<endl;
  159.     for(int i=0; i< lines.size(); i++)
  160.     {
  161.         cout<<"Linha n"<<i<<": Theta " << lines[i].theta/thetaStep << " distancia do centro " << lines[i].r - houghHeight << endl;
  162.     }
  163.  
  164.     int max = 0;
  165.     for (int t = 0; t < maxTheta; t++) {
  166.         for (int r = 0; r < doubleHeight; r++) {
  167.             if (houghArray[t][r] > max) {
  168.                 max = houghArray[t][r];
  169.             }
  170.         }
  171.     }
  172.  
  173.  
  174.     houghImg.create(doubleHeight, maxTheta, CV_8UC1);
  175.  
  176.     // desenha espaço de hough
  177.     for (int t = 0; t < maxTheta; t++) {
  178.         for (int r = 0; r < doubleHeight; r++) {
  179.             double value = 255.0 * ((double) houghArray[t][r]) / (double)max;
  180.             int v = 255 - (int) value;
  181.             houghImg.at<uchar>(r, t) = v;    
  182.         }
  183.     }
  184.  
  185.  
  186.     // desenha linhas
  187.     for(int i=0; i< lines.size(); i++)
  188.     {
  189.         for( int j=0; j<img.cols; j++)
  190.         {
  191.             double realTheta = lines[i].theta;
  192.             double dcos = cos(realTheta);
  193.             double dsin = sin(realTheta);
  194.             double rr = lines[i].r - houghHeight;
  195.             double first = rr - dcos * (j - img.cols/2);
  196.             int y = first / dsin;
  197.             y = img.rows - y;
  198.             y-= img.rows/2;
  199.             if(y >= 0 && y < img.rows)
  200.                 linesImg.at<uchar>(y, j) = 0;
  201.         }
  202.     }
  203.  
  204.  
  205.     cv::imshow( "Original Image", img );
  206.     cv::imshow( "Hough Image", houghImg );
  207.     cv::imshow( "Lines Image", linesImg );
  208.  
  209.     uchar c = 0;
  210.  
  211.     while(c != 27)
  212.     {
  213.         c = cv::waitKey(0);  
  214.     }
  215.  
  216.     return 0;
  217. }
Advertisement
Add Comment
Please, Sign In to add comment