00001
00002
00003
00004
00005 #ifdef _CH_
00006 #pragma package <opencv>
00007 #endif
00008
00009 #define CV_NO_BACKWARD_COMPATIBILITY
00010
00011 #ifndef _EiC
00012
00013
00014
00015 #include <opencv/cv.h>
00016 #include <opencv/highgui.h>
00017
00018
00019 #include <stdio.h>
00020 #include <stdlib.h>
00021 #endif
00022
00023 IplImage* marker_mask = 0;
00024 IplImage* markers = 0;
00025 IplImage* img0 = 0, *img = 0, *img_gray = 0, *wshed = 0;
00026 CvPoint prev_pt = {-1,-1};
00027
00028 void on_mouse( int event, int x, int y, int flags, void* param )
00029 {
00030 if( !img )
00031 return;
00032
00033 if( event == CV_EVENT_LBUTTONUP || !(flags & CV_EVENT_FLAG_LBUTTON) )
00034 prev_pt = cvPoint(-1,-1);
00035 else if( event == CV_EVENT_LBUTTONDOWN )
00036 prev_pt = cvPoint(x,y);
00037 else if( event == CV_EVENT_MOUSEMOVE && (flags & CV_EVENT_FLAG_LBUTTON) )
00038 {
00039 CvPoint pt = cvPoint(x,y);
00040 if( prev_pt.x < 0 )
00041 prev_pt = pt;
00042 cvLine( marker_mask, prev_pt, pt, cvScalarAll(255), 5, 8, 0 );
00043 cvLine( img, prev_pt, pt, cvScalarAll(255), 5, 8, 0 );
00044 prev_pt = pt;
00045 cvShowImage( "image", img );
00046 }
00047 }
00048
00049
00050 int main( int argc, char** argv )
00051 {
00052 char* filename = argc >= 2 ? argv[1] : (char*)"fruits.jpg";
00053 CvMemStorage* storage = cvCreateMemStorage(0);
00054 CvRNG rng = cvRNG(-1);
00055
00056 if( (img0 = cvLoadImage(filename,1)) == 0 )
00057 return 0;
00058
00059 printf( "Hot keys: \n"
00060 "\tESC - quit the program\n"
00061 "\tr - restore the original image\n"
00062 "\tw or SPACE - run watershed algorithm\n"
00063 "\t\t(before running it, roughly mark the areas on the image)\n"
00064 "\t (before that, roughly outline several markers on the image)\n" );
00065
00066 cvNamedWindow( "image", 1 );
00067 cvNamedWindow( "watershed transform", 1 );
00068
00069 img = cvCloneImage( img0 );
00070 img_gray = cvCloneImage( img0 );
00071 wshed = cvCloneImage( img0 );
00072 marker_mask = cvCreateImage( cvGetSize(img), 8, 1 );
00073 markers = cvCreateImage( cvGetSize(img), IPL_DEPTH_32S, 1 );
00074 cvCvtColor( img, marker_mask, CV_BGR2GRAY );
00075 cvCvtColor( marker_mask, img_gray, CV_GRAY2BGR );
00076
00077 cvZero( marker_mask );
00078 cvZero( wshed );
00079 cvShowImage( "image", img );
00080 cvShowImage( "watershed transform", wshed );
00081 cvSetMouseCallback( "image", on_mouse, 0 );
00082
00083 for(;;)
00084 {
00085 int c = cvWaitKey(0);
00086
00087 if( (char)c == 27 )
00088 break;
00089
00090 if( (char)c == 'r' )
00091 {
00092 cvZero( marker_mask );
00093 cvCopy( img0, img );
00094 cvShowImage( "image", img );
00095 }
00096
00097 if( (char)c == 'w' || (char)c == ' ' )
00098 {
00099 CvSeq* contours = 0;
00100 CvMat* color_tab = 0;
00101 int i, j, comp_count = 0;
00102
00103 cvClearMemStorage(storage);
00104
00105
00106
00107 cvFindContours( marker_mask, storage, &contours, sizeof(CvContour),
00108 CV_RETR_CCOMP, CV_CHAIN_APPROX_SIMPLE );
00109 cvZero( markers );
00110 for( ; contours != 0; contours = contours->h_next, comp_count++ )
00111 {
00112 cvDrawContours( markers, contours, cvScalarAll(comp_count+1),
00113 cvScalarAll(comp_count+1), -1, -1, 8, cvPoint(0,0) );
00114 }
00115
00116 if( comp_count == 0 )
00117 continue;
00118
00119 color_tab = cvCreateMat( 1, comp_count, CV_8UC3 );
00120 for( i = 0; i < comp_count; i++ )
00121 {
00122 uchar* ptr = color_tab->data.ptr + i*3;
00123 ptr[0] = (uchar)(cvRandInt(&rng)%180 + 50);
00124 ptr[1] = (uchar)(cvRandInt(&rng)%180 + 50);
00125 ptr[2] = (uchar)(cvRandInt(&rng)%180 + 50);
00126 }
00127
00128 {
00129 double t = (double)cvGetTickCount();
00130 cvWatershed( img0, markers );
00131 t = (double)cvGetTickCount() - t;
00132 printf( "exec time = %gms\n", t/(cvGetTickFrequency()*1000.) );
00133 }
00134
00135
00136 for( i = 0; i < markers->height; i++ )
00137 for( j = 0; j < markers->width; j++ )
00138 {
00139 int idx = CV_IMAGE_ELEM( markers, int, i, j );
00140 uchar* dst = &CV_IMAGE_ELEM( wshed, uchar, i, j*3 );
00141 if( idx == -1 )
00142 dst[0] = dst[1] = dst[2] = (uchar)255;
00143 else if( idx <= 0 || idx > comp_count )
00144 dst[0] = dst[1] = dst[2] = (uchar)0;
00145 else
00146 {
00147 uchar* ptr = color_tab->data.ptr + (idx-1)*3;
00148 dst[0] = ptr[0]; dst[1] = ptr[1]; dst[2] = ptr[2];
00149 }
00150 }
00151
00152 cvAddWeighted( wshed, 0.5, img_gray, 0.5, 0, wshed );
00153 cvShowImage( "watershed transform", wshed );
00154 cvReleaseMat( &color_tab );
00155 }
00156 }
00157
00158 return 1;
00159 }
00160
00161 #ifdef _EiC
00162 main(1,"watershed.cpp");
00163 #endif