1 #include<iostream> 2 #include<opencv2\core\core.hpp> 3 #include<opencv2\highgui\highgui.hpp> 4 #include<opencv2\imgproc\imgproc.hpp> 5 using namespace std; 6 using namespace cv; 7 8 const unsigned char FORE_GROUD = 255; 9 int thresh = 30; 10 int maxArea = 100; 11 int times = 100; 12 13 Point getCenterPoint(Rect rect) 14 { 15 Point cpt; 16 cpt.x = rect.x + cvRound(rect.width/2.0); 17 cpt.y = rect.y + cvRound(rect.height/2.0); 18 return cpt; 19 } 20 21 int main(int argc,char*argv[]) 22 { 23 24 VideoCapture video(0); 25 26 //判断如果video是否可以打开 27 if(!video.isOpened()) 28 return -1; 29 cout<<"Opened"<<endl; 30 31 //用于保存当前帧的图片 32 Mat currentBGRFrame; 33 34 //用来保存上一帧和当前帧的灰度图片 35 Mat previousSecondGrayFrame; 36 Mat previousFirstGrayFrame; 37 Mat currentGaryFrame; 38 39 //保存两次的帧差 40 Mat previousFrameDifference;//previousFrameFirst - previousFrameSecond的差分 41 Mat currentFrameDifference;//currentFrame - previousFrameFirst; 42 43 //用来保存帧差的绝对值 44 Mat absFrameDifferece; 45 46 //用来显示前景 47 Mat previousSegmentation; 48 Mat currentSegmentation; 49 Mat segmentation; 50 51 52 //显示前景 53 namedWindow("segmentation",1); 54 createTrackbar("阈值:","segmentation",&thresh,FORE_GROUD,NULL); 55 createTrackbar("面积:","segmentation",&maxArea,FORE_GROUD,NULL); 56 57 //帧数 58 int numberFrame = 0; 59 60 //形态学处理用到的算子 61 Mat morphologyKernel = getStructuringElement(MORPH_RECT,Size(3,3),Point(-1,-1)); 62 63 for(;;) 64 { 65 //读取当前帧 66 video >> currentBGRFrame; 67 68 //判断当前帧是否存在 69 if(!currentBGRFrame.data) 70 continue; 71 72 numberFrame++; 73 //颜色空间的转换 74 cvtColor(currentBGRFrame,currentGaryFrame,COLOR_BGR2GRAY); 75 76 if( numberFrame == 1) 77 { 78 //保存当前帧的灰度图 79 previousSecondGrayFrame = currentGaryFrame.clone(); 80 81 //显示视频 82 imshow("video",currentBGRFrame); 83 continue; 84 } 85 else if( numberFrame == 2) 86 { 87 //保存当前帧的灰度图 88 previousFirstGrayFrame = currentGaryFrame.clone(); 89 90 //previousFirst - previousSecond 91 subtract(previousFirstGrayFrame,previousSecondGrayFrame,previousFrameDifference,Mat(),CV_16SC1); 92 93 //取绝对值 94 absFrameDifferece = abs(previousFrameDifference); 95 96 //位深的改变 97 absFrameDifferece.convertTo(absFrameDifferece,CV_8UC1,1,0); 98 99 //阈值处理 100 threshold(absFrameDifferece,previousSegmentation,double(thresh),double(FORE_GROUD),THRESH_BINARY); 101 102 //显示视频 103 imshow("video",currentBGRFrame); 104 continue; 105 } 106 107 else 108 { 109 //src1-src2 110 //subtract(currentGaryFrame,previousFirstGrayFrame,currentFrameDifference,Mat(),CV_16SC1); 111 112 //取绝对值 113 //absFrameDifferece = abs(currentFrameDifference); 114 absdiff(currentGaryFrame,previousFirstGrayFrame,absFrameDifferece); 115 116 //位深的改变 117 absFrameDifferece.convertTo(absFrameDifferece,CV_8UC1,1,0); 118 119 //阈值处理 120 threshold(absFrameDifferece,currentSegmentation,double(thresh),double(FORE_GROUD),THRESH_BINARY); 121 122 //与运算 123 bitwise_and(previousSegmentation,currentSegmentation,segmentation); 124 125 //中值滤波 126 medianBlur(segmentation,segmentation,3); 127 128 //形态学处理(开闭运算) 129 //morphologyEx(segmentation,segmentation,MORPH_OPEN,morphologyKernel,Point(-1,-1),1,BORDER_REPLICATE); 130 morphologyEx(segmentation,segmentation,MORPH_CLOSE,morphologyKernel,Point(-1,-1),2,BORDER_REPLICATE); 131 132 133 //找边界 134 vector< vector<Point> > contours; 135 vector<Vec4i> hierarchy; 136 //复制segmentation 137 Mat tempSegmentation = segmentation.clone(); 138 findContours( segmentation, contours, hierarchy, CV_RETR_EXTERNAL, CV_CHAIN_APPROX_SIMPLE, Point(0, 0) );//CV_RETR_TREE 139 vector< vector<Point> > contours_poly( contours.size() ); 140 141 /*存储运动物体*/ 142 Rect rect = Rect(0,0,0,0); 143 vector<Rect> boundRect; 144 boundRect.clear(); 145 146 //画出运动物体 147 for(unsigned int index = 0;index < contours.size() ;index++) 148 { 149 approxPolyDP( Mat(contours[index]), contours_poly[index], 3, true ); 150 Rect tmprect = boundingRect( Mat(contours_poly[index]) ); 151 //cout<<getCenterPoint(rect)<<endl; 152 int currentArea = tmprect.area(); 153 if( currentArea >= rect.area() && currentArea >= maxArea*times ) 154 rect = tmprect; 155 } 156 rectangle(currentBGRFrame,rect,Scalar(0,255,255),2); 157 158 //显示视频 159 imshow("video",currentBGRFrame); 160 161 //前景检测 162 imshow("segmentation",segmentation); 163 164 //保存当前帧的灰度图 165 previousFirstGrayFrame = currentGaryFrame.clone(); 166 167 //保存当前的前景检测 168 previousSegmentation = currentSegmentation.clone(); 169 } 170 171 if(waitKey(33) == ‘q‘) 172 break; 173 174 } 175 return 0; 176 }
时间: 2024-10-10 09:11:06