歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
Linux教程網 >> Linux編程 >> Linux編程 >> MFC+OpenCV實現角點檢測

MFC+OpenCV實現角點檢測

日期:2017/3/1 10:26:36   编辑:Linux編程
  1. // 角點檢測
  2. // 根據《基於OpenCV的計算機視覺技術實現》
  3. #define max_corners 200; // 限定的最大角點數
  4. IplImage* srcImage = 0; // 待處理的源圖像
  5. IplImage* ImageShow = 0; // 存儲顯示帶角點的圖像
  6. IplImage* grayImage = 0; // 原始圖像轉換成的灰階圖像
  7. IplImage* corners1 = 0; // 臨時圖像
  8. IplImage* corners2 = 0; // 臨時圖像
  9. int cornerCount0 = max_corners;
  10. int cornerCount; // 實際測得角點數
  11. int qualityLevel = 0; // 最小質量因子
  12. int minDistance = 15; // 角點最小距離
  13. CvScalar color = CV_RGB(255,0,0); // 繪圖顏色
  14. CvPoint2D32f corners[200]; // 角點坐標
  15. CvRect ROI_rect; // 測試范圍
  16. char chek_area_state = 0; // 鼠標狀態
  17. void re_find_corners(int) // 滑動條響應函數
  18. {
  19. int i,x,y,xl,yu,xr,yd,k;
  20. int radius = 5;
  21. int thickness = 1;
  22. double quality_level = (double) qualityLevel / 100 + 0.02;
  23. double min_distance = (double) minDistance;
  24. cornerCount=cornerCount0; // 設置最大角點數
  25. cvGoodFeaturesToTrack(grayImage, // 角點檢測
  26. corners1,corners2,corners,&cornerCount,
  27. quality_level,min_distance,NULL);
  28. if (cornerCount>0) { // 測到角點
  29. xl=ROI_rect.x; yu=ROI_rect.y; // 設置初始測試范圍
  30. xr=ROI_rect.x+ROI_rect.width;
  31. yd=ROI_rect.y+ROI_rect.height;
  32. cvCopy(srcImage,ImageShow); // 恢復源圖像
  33. for (i=0,k=0;i<cornerCount;i++) {
  34. x=(int)corners[i].x;
  35. y=(int)corners[i].y;
  36. if ((xl<x)&&(x<xr)&&(yu<y)&&(y<yd)) { // 范圍檢查
  37. corners[k].x=corners[i].x; // 保存范圍內角點
  38. corners[k].y=corners[i].y;
  39. k++;
  40. }
  41. }
  42. cornerCount=k; // 范圍內角點數
  43. cvCopy(srcImage,ImageShow);
  44. for (i=0;i<cornerCount;i++) {
  45. x=(int)corners[i].x;
  46. y=(int)corners[i].y;
  47. cvCircle(ImageShow,cvPoint(x,y), // 角點處畫圈
  48. radius,color,thickness,CV_AA,0);
  49. }
  50. cvRectangle(ImageShow,cvPoint(xl,yu),cvPoint(xr,yd),
  51. CV_RGB(0,255,0),thickness,CV_AA,0); // 畫矩形
  52. cvShowImage("image", ImageShow); // 顯示畫圈圖像
  53. }
  54. }
  55. void on_mouse2(int event,int x,int y,int flags,void* param)
  56. { // 鼠標響應函數
  57. int thickness = 1;
  58. CvPoint point1,point2;
  59. if (event == CV_EVENT_LBUTTONDOWN) { // 鼠標左鍵按下
  60. ROI_rect.x = x; // 記錄檢測窗口一角坐標
  61. ROI_rect.y = y;
  62. chek_area_state = 1; // 設置狀態標志
  63. }
  64. else if (chek_area_state && event == CV_EVENT_MOUSEMOVE) { // 鼠標移動
  65. cvCopy(srcImage,ImageShow); // 恢復原始圖像
  66. point1 = cvPoint(ROI_rect.x, ROI_rect.y);
  67. point2 = cvPoint(x,y); // 當前坐標
  68. cvRectangle(ImageShow,point1,point2,CV_RGB(0,255,0),
  69. thickness,CV_AA,0); // 畫矩形
  70. cvShowImage("image", ImageShow); // 顯示檢測結果
  71. cvWaitKey(20); // 延時
  72. }
  73. else if (chek_area_state && event == CV_EVENT_LBUTTONUP) { // 鼠標左鍵抬起
  74. ROI_rect.width = abs(x - ROI_rect.x); // 記錄檢測窗口對角坐標
  75. ROI_rect.height = abs(y - ROI_rect.y);
  76. re_find_corners(0); // 角點檢測
  77. chek_area_state = 0; // 恢復狀態標志
  78. cvWaitKey(20);
  79. }
  80. }
  81. void CCVMFCView::OnCornersTest() // 角點檢測
  82. {
  83. if (workImg->nChannels>1) { // 原圖為真彩色圖像==3
  84. srcImage = cvCloneImage(workImg);
  85. }
  86. else { // 原圖為灰階圖像
  87. srcImage = cvCreateImage(cvGetSize(workImg),IPL_DEPTH_8U,3);
  88. cvCvtColor(workImg,srcImage,CV_GRAY2BGR);
  89. }
  90. cvFlip(srcImage);
  91. grayImage = cvCreateImage(cvGetSize(srcImage),IPL_DEPTH_8U,1);
  92. cvCvtColor(srcImage,grayImage,CV_BGR2GRAY); // 轉換為灰階圖像
  93. ImageShow = cvCloneImage(srcImage);
  94. ROI_rect.x =0;
  95. ROI_rect.y =0;
  96. ROI_rect.width = grayImage->width;
  97. ROI_rect.height = grayImage->height;
  98. corners1 = cvCreateImage(cvGetSize(grayImage),IPL_DEPTH_32F,1);
  99. corners2 = cvCreateImage(cvGetSize(grayImage),IPL_DEPTH_32F,1);
  100. cvNamedWindow("image",0); // 設置顯示窗口
  101. cvResizeWindow("image",325,350); // 改變窗口尺寸
  102. cvCreateTrackbar("角點最小距離", "image", // 設置距離滑動條
  103. &minDistance, 200,re_find_corners);
  104. cvCreateTrackbar("最小質量因子","image", // 設置質量滑動條
  105. &qualityLevel,100,re_find_corners);
  106. re_find_corners(0); // 角點檢測
  107. cvSetMouseCallback("image",on_mouse2,0); // 設置鼠標響應函數
  108. cvWaitKey(0); // 等待鍵輸入
  109. cvDestroyWindow( "image" ); // 關閉窗口
  110. cvReleaseImage(&srcImage); // 釋放圖像存儲單元
  111. cvReleaseImage(&grayImage);
  112. cvReleaseImage(&corners1);
  113. cvReleaseImage(&corners2);
  114. cvFlip(ImageShow);
  115. m_dibFlag=imageReplace(ImageShow,&workImg); // 輸出檢測結果
  116. m_ImageType=-2;
  117. Invalidate();
  118. }
Copyright © Linux教程網 All Rights Reserved