open_door_detector_alg_node.cpp
Go to the documentation of this file.
00001 #include "open_door_detector_alg_node.h"
00002 
00003 using namespace std;
00004 namespace enc = sensor_msgs::image_encodings;
00005 
00006 static const char WINDOW_1[] = "Depth Image";
00007 static const char WINDOW_2[] = "Open Door Detector";
00008 
00009 OpenDoorDetectorAlgNode::OpenDoorDetectorAlgNode(void) :
00010   algorithm_base::IriBaseAlgorithm<OpenDoorDetectorAlgorithm>()
00011 {
00012   //init class attributes if necessary
00013   //this->loop_rate_ = 2;//in [Hz]
00014 
00015   // [init publishers]
00016   this->door_centroid_publisher_ = this->public_node_handle_.advertise<geometry_msgs::PoseStamped>("door_centroid", 1);
00017   this->open_door_coordinates_publisher_ = this->public_node_handle_.advertise<std_msgs::Int32MultiArray>("open_door_coordinates", 1);
00018   
00019   // [init subscribers]
00020   //if (!no_simulator)
00021   this->door_action_start_subscriber_ = this->public_node_handle_.subscribe("/iri_door_detector/door_detector_actions/door_action_start", 1, &OpenDoorDetectorAlgNode::door_action_start_callback, this);
00022 
00023 
00024   // [init services]
00025   
00026   // [init clients]
00027   
00028   // [init action servers]
00029   
00030   // [init action clients]
00031 
00032   // [init algorithm variables]
00033   min_range = 0.5;
00034   max_range = 5.5;
00035 
00036   frame_left=0;
00037   frame_right=0;
00038   frame_up=0;
00039 
00040   start=0;
00041   captured_depth = 0;
00042   support=15;
00043   distance_to_room=0.7;
00044 
00045   white = CV_RGB(255,255,255);
00046   black = CV_RGB(0,0,0);
00047 }
00048 
00049 OpenDoorDetectorAlgNode::~OpenDoorDetectorAlgNode(void)
00050 {
00051   // [free dynamic memory]
00052 }
00053 
00054 void OpenDoorDetectorAlgNode::mainNodeThread(void)
00055 {
00056   // [fill msg structures]
00057   //this->Marker_msg_.data = my_var;
00058   //this->PoseStamped_msg_.data = my_var;
00059   
00060   // [fill srv structure and make request to the server]
00061   
00062   // [fill action structure and make request to the action server]
00063 
00064   // [publish messages]
00065   //this->door_centroid_publisher_.publish(poses);
00066 }
00067 
00068 /*  [subscriber callbacks] */
00069 void OpenDoorDetectorAlgNode::door_action_start_callback(const std_msgs::Int8::ConstPtr& action_start) 
00070 { 
00071   //ROS_INFO("OpenDoorDetectorAlgNode::door_action_start_callback: New Message Received"); 
00072 
00073   //use appropiate mutex to shared variables if necessary 
00074   //this->alg_.lock(); 
00075   this->door_action_start_mutex_.enter(); 
00076 
00077   start=action_start->data;
00078 
00079   if (start==0)
00080   {
00081         image_color_subscriber_.shutdown();
00082         points_subscriber_.shutdown();
00083         //cvDestroyWindow("Open Door Detector");
00084   }
00085   if (start==1)
00086   {  
00087           this->points_subscriber_ = this->public_node_handle_.subscribe("/camera/depth/points", 1, &OpenDoorDetectorAlgNode::points_callback, this);
00088           this->image_color_subscriber_ = this->public_node_handle_.subscribe("/camera/rgb/image_color", 1, &OpenDoorDetectorAlgNode::image_color_callback, this);
00089   }
00090 
00091   //unlock previously blocked shared variables 
00092   //this->alg_.unlock(); 
00093   this->door_action_start_mutex_.exit(); 
00094 }
00095 void OpenDoorDetectorAlgNode::image_color_callback(const sensor_msgs::Image::ConstPtr& image_color) 
00096 { 
00097   //ROS_INFO("OpenDoorDetectorAlgNode::image_color_callback: New Message Received"); 
00098  
00099   //use appropiate mutex to shared variables if necessary 
00100   //this->alg_.lock(); 
00101   this->image_color_mutex_.enter(); 
00102   
00103   if(captured_depth==0)
00104   {
00105           try
00106           {
00107                 //Always copy, returning a mutable CvImage. OpenCV expects color images to use BGR channel order.
00108                 original = cv_bridge::toCvCopy(image_color, enc::BGR8);                                 
00109           }
00110           catch (cv_bridge::Exception& e)
00111           {
00112                 //if there is an error during conversion, display it
00113                 ROS_ERROR("Error while capturing color image: %s", e.what());
00114                 return;
00115           } 
00116   }
00117 
00118   captured_depth=1; 
00119 
00120   //unlock previously blocked shared variables 
00121   //this->alg_.unlock(); 
00122   this->image_color_mutex_.exit(); 
00123 }
00124 void OpenDoorDetectorAlgNode::points_callback(const sensor_msgs::PointCloud2::ConstPtr& points) 
00125 { 
00126   //ROS_INFO("OpenDoorDetectorAlgNode::depth_image_callback: New Message Received"); 
00127 
00128   //use appropiate mutex to shared variables if necessary 
00129   //this->alg_.lock(); 
00130   this->points_mutex_.enter(); 
00131 
00132   if(captured_depth==1)
00133   {           
00134         pcl::fromROSMsg (*points, cloud);
00135 
00136         cv:: Mat depth (original->image.rows, original->image.cols, CV_8UC1);   
00137         
00138         // convert to something visible
00139         for(int i = 0; i < original->image.rows; i++)
00140         {
00141                 Ii = depth.ptr<char>(i);
00142                 for(int j = 0; j < original->image.cols; j++)
00143                 {   
00144                         point3D = cloud.at(j,i);
00145                         Ii[j] = (char) (255*((point3D.z-min_range)/(max_range-min_range)));
00146                 }   
00147         }
00148         //cv::Canny(depth, depth, 50, 50, 3, true);
00149 
00150         step_x=original->image.cols/20;
00151         step_y=original->image.rows/20;
00152 
00153         vec_up.clear();
00154         vec_down.clear();
00155         vec_left.clear();
00156         vec_right.clear();
00157         vec_start=0;
00158         vec_end=0;
00159         
00160         //look for vertical door frames (left to right)
00161         for(int i = 1; i < original->image.rows; i=i+step_y)
00162         {
00163                 p_set=0;
00164                 point=0; 
00165                 for(int j = 1; j < original->image.cols; j++)
00166                 {
00167                         //cv::line(depth, cvPoint(j,i), cvPoint(j,i), CV_RGB(0,0,0), 3, 8, 0); 
00168                         if(point==-1 && cloud.at(j,i).z>=left_depth+distance_to_room && !std::isnan(cloud.at(j,i).z) && cloud.at(j,i).z>0.0 && cloud.at(j,i).z<5.0)
00169                         {                                                       
00170                                 for(int k = 1; k < j; k++)
00171                                 { 
00172                                         if(!std::isnan(cloud.at(k,i).z) && cloud.at(k,i).z>0.0 && cloud.at(k,i).z<5.0)
00173                                         {
00174                                                 if(k<=j-50)
00175                                                 {
00176                                                         x_left=cloud.at(k,i).x;
00177                                                         frame_left=cloud.at(k,i).z;
00178                                                 }
00179                                                 if(k<=j-30)
00180                                                 {
00181                                                         x_right=cloud.at(k,i).x;
00182                                                         frame_right=cloud.at(k,i).z;
00183                                                 }
00184                                         }
00185                                 }
00186                                 dy=frame_right-frame_left;
00187                                 dx=x_right-x_left;
00188                                 if(dx!=0)
00189                                 {
00190                                         m1=dy/dx;
00191                                         b1=frame_left-m1*x_left;
00192 
00193                                         for(int k=j; k<original->image.cols-1; k++)
00194                                         {
00195                                                 if(!std::isnan(cloud.at(k,i).z) && cloud.at(k,i).z>0.0 && cloud.at(k,i).z<5.0)
00196                                                 {
00197                                                         dst=abs(m1*cloud.at(k,i).x-cloud.at(k,i).z+b1)/sqrt(m1*m1+1);
00198                                                         meters= (left_depth+cloud.at(k,i).z)/2;
00199                                                         max_dst_h=max_x/meters;
00200                                                         min_dst_h=min_x/meters;
00201                                                         if(dst<0.1 && abs(k-frame_x)<max_dst_h && abs(k-frame_x)>min_dst_h && abs(left_depth-cloud.at(k,i).z)<0.8) 
00202                                                         {
00203                                                                 if(SVP)
00204                                                                 {cv::line(depth, cvPoint(frame_x,i), cvPoint(frame_x,i), white, 10, 8, 0);
00205                                                                 cv::line(depth, cvPoint(k,i), cvPoint(k,i), black, 10, 8, 0);}
00206                                                                 vec_right.push_back(cvPoint(k,i));
00207                                                                 vec_left.push_back(cvPoint(frame_x,i));
00208                                                                 vec_end++;
00209                                                                 point=0;
00210                                                                 break;
00211                                                         }
00212                                                         if(point==1 && cloud.at(k,i).z<prev_depth-distance_to_room && abs(left_depth-cloud.at(k,i).z)<0.8)
00213                                                         {
00214                                                                 if(SVP)
00215                                                                 {cv::line(depth, cvPoint(frame_x,i), cvPoint(frame_x,i), white, 10, 8, 0);
00216                                                                 cv::line(depth, cvPoint(k,i), cvPoint(k,i), black, 10, 8, 0);}
00217                                                                 vec_right.push_back(cvPoint(k,i));
00218                                                                 vec_left.push_back(cvPoint(frame_x,i));
00219                                                                 vec_end++;
00220                                                                 point=0;
00221                                                                 break;
00222                                                         }
00223                                                         prev_depth=cloud.at(k,i).z;
00224                                                         point=1;
00225                                                 }
00226                                         }
00227                                 }
00228                         }
00229                         if(point!=1 && !std::isnan(cloud.at(j,i).z) && cloud.at(j,i).z>0.0 && cloud.at(j,i).z<5.0)
00230                         {
00231                                 //cv::line(depth, cvPoint(j,i), cvPoint(j,i), CV_RGB(0,0,0), 10, 8, 0);
00232                                 frame_x=j;
00233                                 left_depth=cloud.at(j,i).z;
00234                                 point=-1;
00235                         }
00236                         /*if(j==original->image.cols-1 && p_set==0)
00237                         {
00238                                 if(SVP)
00239                                 {cv::line(depth, cvPoint(original->image.cols-1,i), cvPoint(original->image.cols-1,i), white, 10, 8, 0);
00240                                 cv::line(depth, cvPoint(1,i), cvPoint(1,i), black, 10, 8, 0);}
00241                                 vec_left.push_back(cvPoint(original->image.cols-1,i));
00242                                 vec_right.push_back(cvPoint(1,i));
00243                                 vec_end++;
00244                         }*/
00245                 }   
00246         }
00247         
00248 
00249         //look for vertical door frames (right to left)
00250         for(int i = 1; i < original->image.rows; i=i+step_y)
00251         {
00252                 p_set=0;
00253                 point=0; 
00254                 for(int j = original->image.cols-1; j > 1; j--)
00255                 {
00256                         //cv::line(depth, cvPoint(j,i), cvPoint(j,i), CV_RGB(0,0,0), 3, 8, 0); 
00257                         if(point==-1 && cloud.at(j,i).z>=right_depth+distance_to_room && !std::isnan(cloud.at(j,i).z) && cloud.at(j,i).z>0.0 && cloud.at(j,i).z<5.0)
00258                         {                                                       
00259                                 for(int k = original->image.cols-1; k > j; k--)
00260                                 { 
00261                                         if(!std::isnan(cloud.at(k,i).z) && cloud.at(k,i).z>0.0 && cloud.at(k,i).z<5.0)
00262                                         {
00263                                                 if(k>=j+50)
00264                                                 {
00265                                                         x_right=cloud.at(k,i).x;
00266                                                         frame_right=cloud.at(k,i).z;
00267                                                 }
00268                                                 if(k>=j+30)
00269                                                 {
00270                                                         x_left=cloud.at(k,i).x;
00271                                                         frame_left=cloud.at(k,i).z;
00272                                                 }
00273                                         }
00274                                 }
00275                                 dy=frame_right-frame_left;
00276                                 dx=x_right-x_left;
00277                                 if(dx!=0)
00278                                 {
00279                                         m1=dy/dx;
00280                                         b1=frame_right-m1*x_right;
00281 
00282                                         for(int k=j; k>1; k--)
00283                                         {
00284                                                 if(!std::isnan(cloud.at(k,i).z) && cloud.at(k,i).z>0.0 && cloud.at(k,i).z<5.0)
00285                                                 {
00286                                                         dst=abs(m1*cloud.at(k,i).x-cloud.at(k,i).z+b1)/sqrt(m1*m1+1);
00287                                                         meters= (right_depth+cloud.at(k,i).z)/2;
00288                                                         max_dst_h=max_x/meters;
00289                                                         min_dst_h=min_x/meters;
00290                                                         if(dst<0.1 && abs(k-frame_x)<max_dst_h && abs(k-frame_x)>min_dst_h && abs(right_depth-cloud.at(k,i).z)<0.8) 
00291                                                         {
00292                                                                 if(SVP)
00293                                                                 {cv::line(depth, cvPoint(frame_x,i), cvPoint(frame_x,i), black, 10, 8, 0);
00294                                                                 cv::line(depth, cvPoint(k,i), cvPoint(k,i), white, 10, 8, 0);}
00295                                                                 vec_left.push_back(cvPoint(k,i));
00296                                                                 vec_right.push_back(cvPoint(frame_x,i));
00297                                                                 point=0;
00298                                                                 break;
00299                                                         }
00300                                                         if (point==1 && cloud.at(k,i).z<prev_depth-distance_to_room && abs(right_depth-cloud.at(k,i).z)<0.8)
00301                                                         {
00302                                                                 if(SVP)
00303                                                                 {cv::line(depth, cvPoint(frame_x,i), cvPoint(frame_x,i), black, 10, 8, 0);
00304                                                                 cv::line(depth, cvPoint(k,i), cvPoint(k,i), white, 10, 8, 0);}
00305                                                                 vec_left.push_back(cvPoint(k,i));
00306                                                                 vec_right.push_back(cvPoint(frame_x,i));
00307                                                                 point=0;
00308                                                                 break;
00309                                                         }
00310                                                         prev_depth=cloud.at(k,i).z;
00311                                                         point=1;
00312                                                 }
00313                                         }
00314                                 }
00315                         }
00316                         if(point!=1 && !std::isnan(cloud.at(j,i).z) && cloud.at(j,i).z>0.0 && cloud.at(j,i).z<5.0)
00317                         {
00318                                 //cv::line(depth, cvPoint(j,i), cvPoint(j,i), CV_RGB(0,0,0), 10, 8, 0);
00319                                 frame_x=j;
00320                                 right_depth=cloud.at(j,i).z;
00321                                 point=-1;
00322                         }
00323                         /*if(j==original->image.cols-1 && p_set==0)
00324                         {
00325                                 if(SVP)
00326                                 {cv::line(depth, cvPoint(original->image.cols-1,i), cvPoint(original->image.cols-1,i), white, 10, 8, 0);
00327                                 cv::line(depth, cvPoint(1,i), cvPoint(1,i), black, 10, 8, 0);}
00328                                 vec_left.push_back(cvPoint(original->image.cols-1,i));
00329                                 vec_right.push_back(cvPoint(1,i));
00330                                 vec_end++;
00331                         }*/
00332                 }   
00333         }
00334         
00335         //look for horizontal door frames
00336         for(int j = 1; j < original->image.cols; j=j+step_x)
00337         {  
00338                 p_set=0;
00339                 point=0;
00340                 frame_y=10;
00341                 for(int i = 10; i < original->image.rows; i++)
00342                 {   
00343 
00344                         meters= (cloud.at(j,(int)frame_y).z+cloud.at(j,i).z)/2;
00345                         min_dst_v=(min_y/meters);
00346 
00347                         //cv::line(depth, cvPoint(j,i), cvPoint(j,i), CV_RGB(0,0,0), 3, 8, 0);
00348                         if((abs(cloud.at(j,i).z-frame_up)<0.1 && point==1 && !std::isnan(cloud.at(j,i).z) && abs(i-frame_y)>min_dst_v) || (i==original->image.rows-1 && point==1))
00349                         {
00350                                 if(SVP)
00351                                 {cv::line(depth, cvPoint(j,frame_y), cvPoint(j,frame_y), white, 10, 8, 0);
00352                                 cv::line(depth, cvPoint(j,i), cvPoint(j,i), black, 10, 8, 0);}
00353                                 vec_up.push_back(cvPoint(j,frame_y));
00354                                 vec_down.push_back(cvPoint(j,i));
00355                                 frame_up=0;
00356                                 point=0;
00357                                 p_set=1;
00358                         }
00359                         if(cloud.at(j,i).z>=cloud.at(j,i-10).z+distance_to_room && point==0 && !std::isnan(cloud.at(j,i).z) && !std::isnan(cloud.at(j,i-10).z))
00360                         {
00361                                 //cv::line(depth, cvPoint(j,i), cvPoint(j,i), CV_RGB(255,255,255), 10, 8, 0);
00362                                 frame_up=cloud.at(j,i-10).z;
00363                                 frame_y=i;
00364                                 point=1;
00365                         }
00366                         if(i==original->image.rows-1 && p_set==0)
00367                         {
00368                                 if(SVP)
00369                                 {cv::line(depth, cvPoint(j,0), cvPoint(j,0), white, 10, 8, 0);
00370                                 cv::line(depth, cvPoint(j,original->image.rows-1), cvPoint(j,original->image.rows-1), black, 10, 8, 0);}
00371                                 vec_up.push_back(cvPoint(j,0));
00372                                 vec_down.push_back(cvPoint(j,original->image.rows-1));
00373                         }
00374                 }
00375         }
00376         
00377         ss_door_centroid.clear();
00378         ss_depth.clear();
00379         ss_c1.clear();
00380         ss_c2.clear();
00381         ss_c3.clear();
00382         ss_c4.clear();
00383         if(vec_end==0)
00384                 vec_end=vec_left.size();
00385 
00386         if(min(min(vec_left.size(),vec_right.size()),min(vec_up.size(),vec_down.size()))>0)
00387         {
00388                 for (size_t i=0; i<vec_end-1; i++)
00389                 {
00390                         //after left to right sweep, analyze right to left sweep
00391                         if(i==vec_end-2 && i < vec_left.size()-1)
00392                         {
00393                                 vec_end=vec_left.size();
00394                                 if(i+2<vec_end-1)
00395                                         i=i+2;          
00396                         }
00397                         for (size_t j=0; j<min(vec_up.size(),vec_down.size())-1; j++)
00398                         {
00399                                 f_c1=0;
00400                                 f_c2=0;
00401                                 f_c3=0;
00402                                 f_c4=0;
00403                                 
00404                                 //look for the next left marker which is nearest to left marker i
00405                                 check=0;
00406                                 offset_l=0;
00407                                 dst=original->image.cols*2;
00408                                 while(check==0)
00409                                 {
00410                                         while(vec_left.at(i+1+offset_l).y==vec_left.at(i).y)
00411                                         {
00412                                                 offset_l++;
00413                                                 if(i+1+offset_l>vec_end-2)
00414                                                 {
00415                                                         offset_l--;
00416                                                         break;
00417                                                 }
00418                                         }
00419                                         if(i+1+offset_l>vec_end-2)
00420                                         {
00421                                                 offset_l--;
00422                                                 break;
00423                                         }
00424                                         dst=min(dst,abs(vec_left.at(i+1+offset_l).x-vec_left.at(i).x));
00425                                         if(i+2+offset_l<vec_end-1)
00426                                         {               
00427                                                 if(vec_left.at(i+2+offset_l).y>vec_left.at(i+1+offset_l).y)
00428                                                 {
00429                                                         check=1;
00430                                                 }               
00431                                         }
00432                                         if(check==0)
00433                                                 offset_l++;
00434                                 }
00435                                 if(offset_l>0)
00436                                 {
00437                                         for(int k=0; k<=offset_l; k++)
00438                                         {
00439                                                 if(abs(vec_left.at(i+1+k).x-vec_left.at(i).x)==dst)
00440                                                 {
00441                                                         offset_l=k;
00442                                                 }
00443                                         }
00444                                 }
00445                                         
00446                                 //look for the next up marker which is nearest to up marker i
00447                                 check=0;
00448                                 offset_u=0;
00449                                 dst=original->image.cols*2;
00450                                 while(check==0)
00451                                 {
00452                                         while(vec_up.at(j+1+offset_u).x==vec_up.at(j).x)
00453                                         {
00454                                                 offset_u++;
00455                                                 if(j+1+offset_u>vec_up.size()-2)
00456                                                 {
00457                                                         offset_u--;
00458                                                         break;
00459                                                 }
00460                                         }
00461                                         if(j+1+offset_u>vec_up.size()-2)
00462                                         {
00463                                                 offset_u--;
00464                                                 break;
00465                                         }
00466                                         dst=min(dst,abs(vec_up.at(j+1+offset_u).y-vec_up.at(j).y));
00467                                         if(j+2+offset_u<vec_up.size()-1)
00468                                         {               
00469                                                 if(vec_up.at(j+2+offset_u).x>vec_up.at(j+1+offset_u).x)
00470                                                 {
00471                                                         check=1;
00472                                                 }
00473                                         }
00474                                         if(check==0)
00475                                                 offset_u++;             
00476                                 }
00477                                 if(offset_u>0)
00478                                 {
00479                                         for(int k=0; k<=offset_u; k++)
00480                                         {
00481                                                 if(abs(vec_up.at(j+1+k).y-vec_up.at(j).y)==dst)
00482                                                 {
00483                                                         offset_u=k;
00484                                                 }
00485                                         }
00486                                 }
00487 
00488                                 //look for the next right marker which is nearest to right marker i
00489                                 check=0;
00490                                 offset_r=0;
00491                                 dst=original->image.cols*2;
00492                                 while(check==0)
00493                                 {
00494                                         while(vec_right.at(i+1+offset_r).y==vec_right.at(i).y)
00495                                         {
00496                                                 offset_r++;
00497                                                 if(i+1+offset_r>vec_end-2)
00498                                                 {
00499                                                         offset_r--;
00500                                                         break;
00501                                                 }
00502                                         }
00503                                         if(i+1+offset_r>vec_end-2)
00504                                         {
00505                                                 offset_r--;
00506                                                 break;
00507                                         }
00508                                         dst=min(dst,abs(vec_right.at(i+1+offset_r).x-vec_right.at(i).x));
00509                                         if(i+2+offset_r<vec_end-1)
00510                                         {               
00511                                                 if(vec_right.at(i+2+offset_r).y>vec_right.at(i+1+offset_r).y)
00512                                                 {
00513                                                         check=1;
00514                                                 }               
00515                                         }
00516                                         if(check==0)
00517                                                 offset_r++;
00518                                 }
00519                                 if(offset_r>0)
00520                                 {
00521                                         for(int k=0; k<=offset_r; k++)
00522                                         {
00523                                                 if(abs(vec_right.at(i+1+k).x-vec_right.at(i).x)==dst)
00524                                                 {
00525                                                         offset_r=k;
00526                                                 }
00527                                         }
00528                                 }
00529 
00530                                 //look for the next down marker which is nearest to down marker i                       
00531                                 check=0;
00532                                 offset_d=0;
00533                                 dst=original->image.cols*2;
00534                                 while(check==0)
00535                                 {
00536                                         while(vec_down.at(j+1+offset_d).x==vec_down.at(j).x)
00537                                         {
00538                                                 offset_d++;
00539                                                 if(j+1+offset_d>vec_down.size()-2)
00540                                                 {
00541                                                         offset_d--;
00542                                                         break;
00543                                                 }
00544                                         }
00545                                         if(j+1+offset_d>vec_down.size()-2)
00546                                         {
00547                                                 offset_d--;
00548                                                 break;
00549                                         }
00550                                         dst=min(dst,abs(vec_down.at(j+1+offset_d).y-vec_down.at(j).y));
00551                                         if(j+2+offset_d<vec_down.size()-1)
00552                                         {               
00553                                                 if(vec_down.at(j+2+offset_d).x>vec_down.at(j+1+offset_d).x)
00554                                                 {
00555                                                         check=1;
00556                                                 }
00557                                         }
00558                                         if(check==0)
00559                                                 offset_d++;             
00560                                 }
00561                                 if(offset_d>0)
00562                                 {
00563                                         for(int k=0; k<=offset_d; k++)
00564                                         {
00565                                                 if(abs(vec_down.at(j+1+k).y-vec_down.at(j).y)==dst)
00566                                                 {
00567                                                         offset_d=k;     
00568                                                 }
00569                                         }
00570                                 }
00571 
00572                                 if(SVL)
00573                                 {
00574                                         cv::line(depth, cvPoint(vec_left.at(i).x,vec_left.at(i).y), cvPoint(vec_left.at(i+1+offset_l).x,vec_left.at(i+1+offset_l).y), CV_RGB(255,255,255), 2, 8, 0);
00575                                         cv::line(depth, cvPoint(vec_up.at(j).x,vec_up.at(j).y), cvPoint(vec_up.at(j+1+offset_u).x,vec_up.at(j+1+offset_u).y), CV_RGB(255,255,255), 2, 8, 0);    
00576                                         cv::line(depth, cvPoint(vec_right.at(i).x,vec_right.at(i).y), cvPoint(vec_right.at(i+1+offset_r).x,vec_right.at(i+1+offset_r).y), CV_RGB(255,255,255), 2, 8, 0);        
00577                                         cv::line(depth, cvPoint(vec_down.at(j).x,vec_down.at(j).y), cvPoint(vec_down.at(j+1+offset_d).x,vec_down.at(j+1+offset_d).y), CV_RGB(255,255,255), 2, 8, 0);
00578                                 }
00579 
00580                                 //if(vec_up.at(j).x>=vec_left.at(i).x && vec_up.at(j).y<=vec_left.at(i).y)
00581                                 //{
00582                                         //get c1
00583                                         dy=(vec_left.at(i+1+offset_l).y-vec_left.at(i).y);
00584                                         dx=(vec_left.at(i+1+offset_l).x-vec_left.at(i).x);
00585                                         m1=dy/(dx+0.0001);
00586                                         b1=(vec_left.at(i+1+offset_l).y-m1*vec_left.at(i+1+offset_l).x);
00587 
00588                                         dy=(vec_up.at(j+1+offset_u).y-vec_up.at(j).y);
00589                                         dx=(vec_up.at(j+1+offset_u).x-vec_up.at(j).x);
00590                                         m2=dy/(dx+0.0001);
00591                                         b2=(vec_up.at(j+1+offset_u).y-m2*vec_up.at(j+1+offset_u).x);
00592 
00593                                         x = (b2 - b1)/(m1 - m2 + 0.0001);
00594                                         y = (m1*x)+b1;
00595 
00596                                         if(x<0)
00597                                                 x=0;
00598                                         if(y<0)
00599                                                 y=0;
00600                                         if(x>=original->image.cols)     
00601                                                 x=original->image.cols-1;
00602                                         if(y>=original->image.rows)     
00603                                                 y=original->image.rows-1;
00604 
00605                                         f_c1=1;
00606                                         c1= cvPoint((int)x,(int)y);
00607                                 //}
00608 
00609                                 //if(vec_up.at(j+1+offset_u).x<=vec_right.at(i).x && vec_up.at(j+1+offset_u).y<=vec_right.at(i).y)
00610                                 //{
00611                                         //get c2
00612                                         dy=(vec_right.at(i+1+offset_r).y-vec_right.at(i).y);
00613                                         dx=(vec_right.at(i+1+offset_r).x-vec_right.at(i).x);
00614                                         m1=dy/(dx+0.0001);
00615                                         b1=(vec_right.at(i+1+offset_r).y-m1*vec_right.at(i+1+offset_r).x);
00616 
00617                                         dy=(vec_up.at(j+1+offset_u).y-vec_up.at(j).y);
00618                                         dx=(vec_up.at(j+1+offset_u).x-vec_up.at(j).x);
00619                                         m2=dy/(dx+0.0001);
00620                                         b2=(vec_up.at(j+1+offset_u).y-m2*vec_up.at(j+1+offset_u).x);
00621 
00622                                         x = (b2 - b1)/(m1 - m2 + 0.0001);
00623                                         y = (m1*x)+b1;
00624 
00625                                         if(x<0)
00626                                                 x=0;
00627                                         if(y<0)
00628                                                 y=0;
00629                                         if(x>=original->image.cols)     
00630                                                 x=original->image.cols-1;
00631                                         if(y>=original->image.rows)     
00632                                                 y=original->image.rows-1;
00633 
00634                                         f_c2=1;
00635                                         c2= cvPoint((int)x,(int)y);     
00636                                 //}                             
00637 
00638                                 //if(vec_down.at(j+1+offset_d).x<=vec_right.at(i+1+offset_r).x && vec_down.at(j+1+offset_d).y>=vec_right.at(i+1+offset_r).y)
00639                                 //{
00640                                         //get c3
00641                                         dy=(vec_right.at(i+1+offset_r).y-vec_right.at(i).y);
00642                                         dx=(vec_right.at(i+1+offset_r).x-vec_right.at(i).x);
00643                                         m1=dy/(dx+0.0001);
00644                                         b1=(vec_right.at(i+1+offset_r).y-m1*vec_right.at(i+1+offset_r).x);
00645 
00646                                         dy=(vec_down.at(j+1+offset_d).y-vec_down.at(j).y);
00647                                         dx=(vec_down.at(j+1+offset_d).x-vec_down.at(j).x);
00648                                         m2=dy/(dx+0.0001);
00649                                         b2=(vec_down.at(j+1+offset_d).y-m2*vec_down.at(j+1+offset_d).x);
00650 
00651                                         x = (b2 - b1)/(m1 - m2 + 0.0001);
00652                                         y = (m1*x)+b1;
00653                         
00654                                         if(x<0)
00655                                                 x=0;
00656                                         if(y<0)
00657                                                 y=0;
00658                                         if(x>=original->image.cols)     
00659                                                 x=original->image.cols-1;
00660                                         if(y>=original->image.rows)     
00661                                                 y=original->image.rows-1;
00662 
00663                                         f_c3=1;
00664                                         c3= cvPoint((int)x,(int)y);     
00665                                 //}
00666                                 
00667                                 //if(vec_down.at(j).x>=vec_left.at(i+1+offset_l).x && vec_down.at(j).y>=vec_left.at(i+1+offset_l).y)
00668                                 //{
00669                                         //get c4
00670                                         dy=(vec_left.at(i+1+offset_l).y-vec_left.at(i).y);
00671                                         dx=(vec_left.at(i+1+offset_l).x-vec_left.at(i).x);
00672                                         m1=dy/(dx+0.0001);
00673                                         b1=(vec_left.at(i+1+offset_l).y-m1*vec_left.at(i+1+offset_l).x);
00674 
00675                                         dy=(vec_down.at(j+1+offset_d).y-vec_down.at(j).y);
00676                                         dx=(vec_down.at(j+1+offset_d).x-vec_down.at(j).x);
00677                                         m2=dy/(dx+0.0001);
00678                                         b2=(vec_down.at(j+1+offset_d).y-m2*vec_down.at(j+1+offset_d).x);
00679 
00680                                         x = (b2 - b1)/(m1 - m2 + 0.0001);
00681                                         y = (m1*x)+b1;
00682                 
00683                                         if(x<0)
00684                                                 x=0;
00685                                         if(y<0)
00686                                                 y=0;
00687                                         if(x>=original->image.cols)     
00688                                                 x=original->image.cols-1;
00689                                         if(y>=original->image.rows)     
00690                                                 y=original->image.rows-1;
00691 
00692                                         c4= cvPoint((int)x,(int)y);
00693                                         f_c4=1;
00694                                 //}     
00695         
00696                                 if(f_c1*f_c2*f_c3*f_c4>0)
00697                                 {
00698                                         //distance between corners
00699                                         dst_up=sqrt((c2.x-c1.x)*(c2.x-c1.x)+(c2.y-c1.y)*(c2.y-c1.y));
00700                                         dst_right=sqrt((c3.x-c2.x)*(c3.x-c2.x)+(c3.y-c2.y)*(c3.y-c2.y));
00701                                         dst_down=sqrt((c4.x-c3.x)*(c4.x-c3.x)+(c4.y-c3.y)*(c4.y-c3.y));
00702                                         dst_left=sqrt((c4.x-c1.x)*(c4.x-c1.x)+(c4.y-c1.y)*(c4.y-c1.y));
00703 
00704                                         //compute angles between line pairs
00705                                         theta1 = AngleBetweenLines (c1, c2, c2, c3);
00706                                         theta2 = AngleBetweenLines (c2, c3, c4, c3);
00707                                         theta3 = AngleBetweenLines (c4, c3, c1, c4);
00708                                         theta4 = AngleBetweenLines (c1, c2, c1, c4);
00709                         
00710                                         theta=min(min(theta1,theta2),min(theta3,theta4));
00711                                         dst_h=(dst_down+dst_up)/2;
00712                                         dst_v=(dst_left+dst_right)/2;
00713 
00714                                         cx_min=min(min(c1.x,c2.x),min(c3.x,c4.x));
00715                                         cx_max=max(max(c1.x,c2.x),max(c3.x,c4.x));
00716                                         cy_min=min(min(c1.y,c2.y),min(c3.y,c4.y));
00717                                         cy_max=max(max(c1.y,c2.y),max(c3.y,c4.y));
00718 
00719                                         if (cx_min<0)                                           
00720                                                 cx_min=0;                       if (cx_max<4)
00721                                                                                         cx_max=4;
00722                                         if (cy_min<0)                                           
00723                                                 cy_min=0;                       if (cy_max<4)
00724                                                                                         cy_max=4;
00725                                         if (cx_min>original->image.cols-5)                                              
00726                                                 cx_min=original->image.cols-5;  if (cx_max>original->image.cols-1)
00727                                                                                         cx_max=original->image.cols-1;
00728                                         if (cy_min>original->image.rows-5)                                              
00729                                                 cy_min=original->image.rows-5;  if (cy_max>original->image.rows-1)
00730                                                                                         cy_max=original->image.rows-1;
00731                                         roi_x=abs(cx_max-cx_min);
00732                                         roi_y=abs(cy_max-cy_min);
00733 
00734                                         //Look for door frame depth
00735                                         x_1=(int)((c1.x+c4.x)/2);
00736                                         x_2=(int)((c2.x+c3.x)/2);
00737                                         meters=0;
00738                                         right_depth=1000;
00739                                         left_depth=1000;
00740                                         for (int i=cy_min+roi_y/2; i<cy_min+roi_y*2/3; i++)
00741                                         {
00742                 
00743                                                 if(!std::isnan(cloud.at(x_1,i).z) && cloud.at(x_1,i).z>0.0 && cloud.at(x_1,i).z<5.0)
00744                                                 {
00745                                                         left_depth=min(left_depth,cloud.at(x_1,i).z);
00746                                                 }
00747                                                 if(!std::isnan(cloud.at(x_2,i).z) && cloud.at(x_2,i).z>0.0 && cloud.at(x_2,i).z<5.0)
00748                                                 {
00749                                                         right_depth=min(right_depth,cloud.at(x_2,i).z);
00750                                                 }
00751 
00752                                         }
00753                                         meters=(left_depth+right_depth)/2;
00754                                         min_depth=min(left_depth,right_depth);
00755                                         min_dst_h=(min_x/meters);
00756                                         max_dst_h=(max_x/meters);
00757                                         min_dst_v=(min_y/meters);
00758                                         max_dst_v=(max_y/meters);
00759 
00760                                         door_x=(int)(cx_min+roi_x/2);
00761                                         door_y=(int)(cy_min+roi_y/2);
00762 
00763                                         room_frame_height=0;
00764                                         lintel=10000;
00765                                         sill=0;
00766 
00767                                         point=0;
00768                                         for(int m=cy_min; m<cy_max; m++)
00769                                         {                               
00770                                                 point3D=cloud.at(door_x,m);
00771                                                 if(!std::isnan(point3D.z) && point3D.z > 0.0 && point3D.z < 5.0) 
00772                                                 {
00773                                                         if(point==1 && point3D.z > (prev_depth+meters)/2 + distance_to_room)
00774                                                         {
00775                                                                 lintel=min(lintel,m);
00776                                                         }
00777                                                         if(point3D.z > min_depth)
00778                                                         {
00779                                                                 sill=max(sill,m);
00780                                                                 //cv::line(depth, cvPoint(door_x,m), cvPoint(door_x,m), CV_RGB(0,0,0), 1, 8, 0);
00781                                                         }
00782                                                         prev_depth=point3D.z;
00783                                                         point=1;
00784                                                 }               
00785                                         }
00786 
00787                                         c3.y=min((int)c3.y,sill);
00788                                         c4.y=min((int)c4.y,sill);
00789                                         r=((double)b_c3.y-(double)cy_min)/((double)cy_max-(double)cy_min);
00790                                         c3.x=b_c2.x+(c3.x-c2.x)*r;
00791                                         c4.x=b_c1.x+(c4.x-c1.x)*r;
00792 
00793                                         c1.y=max((int)c1.y,lintel);
00794                                         c2.y=max((int)c2.y,lintel);
00795                                         r=((double)b_c1.y-(double)cy_min)/((double)cy_max-(double)cy_min);
00796                                         c2.x=c2.x+(c3.x-c2.x)*r;
00797                                         c1.x=c1.x+(c4.x-c1.x)*r;
00798 
00799                                         if(cx_min <= 10 || cx_max >= original->image.cols-10)
00800                                                 min_dst_h=min_dst_h/2;
00801                                         if(cy_min <= 10 || cy_max >= original->image.rows-10)
00802                                                 min_dst_v=min_dst_v/3;
00803                                         
00804                                         //filter false doors using physical constraints
00805                                         sensor_range = (meters>0.1 && !std::isnan(meters) && meters<5.0);
00806                                         perspective = (abs(dst_up-dst_down)<roi_x/2 && abs(dst_left-dst_right)<roi_y/2 && theta>0.698132);
00807                                         geometry = (c4.x<c3.x && c1.x<c2.x && c4.y>c1.y && c3.y>c2.y);
00808                                         size = (dst_h<max_dst_h && dst_v>min_dst_v && dst_v<max_dst_v && roi_x>5 && roi_y>5);
00809 
00810                                         if(!Range_filter)
00811                                                 sensor_range =1; 
00812                                         if(!Persp_filter)
00813                                                 perspective=1; 
00814                                         if(!Geom_filter)
00815                                                 geometry=1; 
00816                                         if(!Size_filter)
00817                                                 size=1; 
00818 
00819                                         if(sensor_range && perspective && geometry && size)
00820                                         {
00821                                                                 
00822                                                 //prepare locations of the selected door frames for the output message  
00823                                                 ss_door_centroid.push_back(cvPoint(door_x,door_y));
00824                                                 ss_depth.push_back(meters);
00825                                                 ss_c1.push_back(c1);
00826                                                 ss_c2.push_back(c2);
00827                                                 ss_c3.push_back(c3);
00828                                                 ss_c4.push_back(c4);
00829                                                 if(SFC)
00830                                                         DrawRect (depth, c1, c2, c3, c4, CV_RGB(100,100,100), 2, 0);
00831                                         }
00832                                 }
00833                         }
00834                 }
00835         }
00836 
00837         //Door size calibration
00838         min_depth=1000;
00839         for (int i=(int)(original->image.cols*1/3); i<(int)(original->image.cols*2/3); i++)
00840         {
00841         
00842                 if(!std::isnan(cloud.at(i,(int)(original->image.rows/2)).z) && cloud.at(i,(int)(original->image.rows/2)).z>0.0 && cloud.at(i,(int)(original->image.rows/2)).z<5.0)
00843                         min_depth=min(min_depth,cloud.at(i,(int)(original->image.rows/2)).z);
00844         }
00845         
00846         min_dst_h=(min_x/min_depth);
00847         max_dst_h=(max_x/min_depth);
00848         min_dst_v=(min_y/min_depth);
00849         max_dst_v=(max_y/min_depth);
00850         
00851         if(DSC)
00852                 DoorSizeCalibration (depth, min_dst_h, max_dst_h, min_dst_v, max_dst_v);
00853 
00854         if (ss_door_centroid.size()>0)
00855         {
00856                 b_door_centroid=cvPoint(0,0);
00857                 b_c1=cvPoint(0,0);
00858                 b_c2=cvPoint(0,0);
00859                 b_c3=cvPoint(0,0);
00860                 b_c4=cvPoint(0,0);
00861                 b_depth=0;
00862 
00863                 for (size_t i=0; i<ss_door_centroid.size(); i++)
00864                 {
00865                         b_door_centroid.x=(int)(b_door_centroid.x+ss_door_centroid.at(i).x);
00866                         b_door_centroid.y=(int)(b_door_centroid.y+ss_door_centroid.at(i).y);
00867                         b_c1.x=(int)(b_c1.x+ss_c1.at(i).x);
00868                         b_c1.y=(int)(b_c1.y+ss_c1.at(i).y);
00869                         b_c2.x=(int)(b_c2.x+ss_c2.at(i).x);
00870                         b_c2.y=(int)(b_c2.y+ss_c2.at(i).y);
00871                         b_c3.x=(int)(b_c3.x+ss_c3.at(i).x);
00872                         b_c3.y=(int)(b_c3.y+ss_c3.at(i).y);
00873                         b_c4.x=(int)(b_c4.x+ss_c4.at(i).x);
00874                         b_c4.y=(int)(b_c4.y+ss_c4.at(i).y);
00875                 }
00876                 b_door_centroid.x=(int)(b_door_centroid.x/ss_door_centroid.size());
00877                 b_door_centroid.y=(int)(b_door_centroid.y/ss_door_centroid.size());
00878                 b_c1.x=(int)(b_c1.x/ss_door_centroid.size());
00879                 b_c1.y=(int)(b_c1.y/ss_door_centroid.size());
00880                 b_c2.x=(int)(b_c2.x/ss_door_centroid.size());
00881                 b_c2.y=(int)(b_c2.y/ss_door_centroid.size());
00882                 b_c3.x=(int)(b_c3.x/ss_door_centroid.size());
00883                 b_c3.y=(int)(b_c3.y/ss_door_centroid.size());
00884                 b_c4.x=(int)(b_c4.x/ss_door_centroid.size());
00885                 b_c4.y=(int)(b_c4.y/ss_door_centroid.size());
00886 
00887                 //TODO--function for cx_min and cx_max!
00888                 cx_min=min(min(b_c1.x,b_c2.x),min(b_c3.x,b_c4.x));
00889                 cx_max=max(max(b_c1.x,b_c2.x),max(b_c3.x,b_c4.x));
00890                 cy_min=min(min(b_c1.y,b_c2.y),min(b_c3.y,b_c4.y));
00891                 cy_max=max(max(b_c1.y,b_c2.y),max(b_c3.y,b_c4.y));
00892                                                                         
00893                 //DrawRect (depth, b_c1, b_c2, b_c3, b_c4, CV_RGB(255,255,255), 3, 0);
00894 
00895                 if (cx_min<0)                                           
00896                         cx_min=0;                       if (cx_max<4)
00897                                                                 cx_max=4;
00898                 if (cy_min<0)                                           
00899                         cy_min=0;                       if (cy_max<4)
00900                                                                 cy_max=4;
00901                 if (cx_min>original->image.cols-5)                                              
00902                         cx_min=original->image.cols-5;  if (cx_max>original->image.cols-1)
00903                                                                 cx_max=original->image.cols-1;
00904                 if (cy_min>original->image.rows-5)                                              
00905                         cy_min=original->image.rows-5;  if (cy_max>original->image.rows-1)
00906                                                                 cy_max=original->image.rows-1;
00907                 
00908                 roi_x=abs(cx_max-cx_min);
00909                 roi_y=abs(cy_max-cy_min);
00910                 r=(double)roi_x/(double)roi_y;  
00911 
00912                 //Look for door frame depth
00913                 x_1=(int)((b_c1.x+b_c4.x)/2);
00914                 x_2=(int)((b_c2.x+b_c3.x)/2);
00915                 min_depth=0;
00916                 right_depth=1000;
00917                 left_depth=1000;
00918                 for (int i=cy_min+roi_y/2; i<cy_min+roi_y*2/3; i++)
00919                 {
00920                 
00921                         if(!std::isnan(cloud.at(x_1,i).z) && cloud.at(x_1,i).z>0.0 && cloud.at(x_1,i).z<5.0)
00922                         {
00923                                 left_depth=min(left_depth,cloud.at(x_1,i).z);
00924                                 cv::line(depth, cvPoint(x_1,i), cvPoint(x_1,i),white, 3, 8, 0);
00925                         }
00926                         if(!std::isnan(cloud.at(x_2,i).z) && cloud.at(x_2,i).z>0.0 && cloud.at(x_2,i).z<5.0)
00927                         {
00928                                 right_depth=min(right_depth,cloud.at(x_2,i).z);
00929                                 cv::line(depth, cvPoint(x_2,i), cvPoint(x_2,i),white, 3, 8, 0);
00930                         }
00931 
00932                 }
00933                 min_depth=(left_depth+right_depth)/2;
00934                 min_dst_h=(min_x/min_depth);
00935                 max_dst_h=(max_x/min_depth);
00936                 min_dst_v=(min_y/min_depth);
00937                 max_dst_v=(max_y/min_depth);
00938                 size=0;
00939                 size=(abs(x_1-x_2)<max_dst_h);
00940 
00941 
00942                 if(s_door_centroid.x>0 && s_door_centroid.y>0)
00943                 {
00944                         dx=abs(b_door_centroid.x-s_door_centroid.x);
00945                         dy=abs(b_door_centroid.y-s_door_centroid.y);
00946                         dst=sqrt(dx*dx+dy*dy);
00947                         if(dst<min_dst_h/4)
00948                                 support++;
00949                 }
00950                 
00951                 s_door_centroid.x=b_door_centroid.x;
00952                 s_door_centroid.y=b_door_centroid.y;
00953         }
00954         
00955         if(ss_door_centroid.size()==0)
00956                 support--;
00957         if(support < 0)
00958         {
00959                 support=0;
00960                 s_door_centroid.x=0;
00961                 s_door_centroid.y=0;
00962         }
00963 
00964         if(support >10)
00965                 support=10;
00966 
00967         cv::Mat depth_graph;
00968         depth_graph = cv::Mat::zeros(depth.rows, depth.cols, CV_8UC1);
00969 
00970         cv::Mat panel_mask;
00971         panel_mask = cv::Mat::zeros(depth.rows, depth.cols, CV_8UC1);
00972 
00973         if(ss_door_centroid.size()>0)
00974         {
00975                 /*Initilalize door state (0 = fully open door,
00976                 -2, -1 = open left, 1, 2 = open right)*/
00977                 side=0.0;
00978                 
00979                 //if the door is not fully open, find jambs
00980                 if(size)
00981                 {
00982                         door_y=(int)((cy_min+cy_max)/2);
00983                         point=0;
00984                         left_depth=1000;
00985                         for(int k=1; k<original->image.cols-1; k++)
00986                         {
00987                                 if(!std::isnan(cloud.at(k,door_y).x) && !std::isnan(cloud.at(k,door_y).z) && cloud.at(k,door_y).z>0.0 && cloud.at(k,door_y).z<5.0)
00988                                 {
00989                                         if(k<(int)(-40.0-5.0/r+(b_c1.x+b_c4.x)/2)) 
00990                                         {       
00991                                                 x_left=cloud.at(k,door_y).x;
00992                                                 frame_left=cloud.at(k,door_y).z;
00993                                                 point=1;
00994                                         }
00995                                         if(k<(int)((b_c1.x+b_c4.x)/2)-10) 
00996                                         {
00997                                                 x_right=cloud.at(k,door_y).x;
00998                                                 frame_right=cloud.at(k,door_y).z;
00999                                                 left_door_end=k;
01000                                                 point=1;
01001 
01002                                                 if(point==1)
01003                                                         cv::line(depth_graph, cvPoint((int)((x_left+2)*150),(int)(frame_left*100)), cvPoint((int)((2+cloud.at(k,door_y).x)*150),(int)(cloud.at(k,door_y).z*100)),white, 1, 8, 0);
01004 
01005                                         }
01006                                         if(k>(int)(-40.0-5.0/r+(b_c1.x+b_c4.x)/2) && k<(int)((b_c1.x+b_c4.x)/2))
01007                                         {
01008                                                 cv::line(depth, cvPoint(k,door_y),cvPoint(k,door_y),white, 1, 8, 0);
01009                                                 left_depth=min(left_depth,cloud.at(k,door_y).z);
01010                                                 y_i=cloud.at(k,door_y).y;
01011                                         }
01012                                 }
01013                         }
01014         
01015                         dy=(frame_right-frame_left)*100;
01016                         dx=(x_right-x_left)*150;
01017                         m1=dy/(dx+0.00001);
01018                         b1=frame_right*100-m1*(x_right+2)*150;
01019         
01020                         point=0;
01021                         right_depth=1000;
01022                         for(int k=original->image.cols-1; k>1; k--)
01023                         {
01024                                 if(!std::isnan(cloud.at(k,door_y).x) && !std::isnan(cloud.at(k,door_y).z) && cloud.at(k,door_y).z>0.0 && cloud.at(k,door_y).z<5.0)
01025                                 {
01026                                         if(k>(int)(40.0+5.0/r+(b_c2.x+b_c3.x)/2)) 
01027                                         {       
01028                                                 x_right=cloud.at(k,door_y).x;
01029                                                 frame_right=cloud.at(k,door_y).z;
01030                                                 point=1;
01031                                         }
01032                                         if(k>(int)((b_c2.x+b_c3.x)/2)+10) 
01033                                         {
01034                                                 x_left=cloud.at(k,door_y).x;
01035                                                 frame_left=cloud.at(k,door_y).z;
01036                                                 point=1;
01037                                                 right_door_end=k;
01038 
01039                                                 if(point==1)
01040                                                         cv::line(depth_graph, cvPoint((int)((x_left+2)*150),(int)(frame_left*100)), cvPoint((int)((2+cloud.at(k,door_y).x)*150),(int)(cloud.at(k,door_y).z*100)),white, 1, 8, 0);
01041 
01042                                         }
01043                                         if(k<(int)(40.0+5.0/r+(b_c2.x+b_c3.x)/2) && k>(int)((b_c2.x+b_c3.x)/2))
01044                                         {
01045                                                 cv::line(depth, cvPoint(k,door_y),cvPoint(k,door_y),white, 1, 8, 0);
01046                                                 right_depth=min(right_depth,cloud.at(k,door_y).z);
01047                                                 y_i=cloud.at(k,door_y).y;
01048                                         }
01049                                 }
01050                         }
01051 
01052                         //cv::line(depth_graph, cvPoint((int)(x_left*150),(int)(frame_left*100)), cvPoint((int)(x_right*150),(int)(frame_right*100)),white, 3, 8, 0);
01053 
01054                         dy=(frame_right-frame_left)*100;
01055                         dx=(x_right-x_left)*150;
01056                         m2=dy/(dx+0.00001);
01057                         b2=frame_left*100-m2*(x_left+2)*150;
01058                 
01059                         x = (b2 - b1)/(m1 - m2 + 0.0001);
01060 
01061                         if(x>(x_left+2)*150)
01062                         {
01063                                 door_end=right_door_end;
01064                                 side=1;
01065                                 y = (m2*depth_graph.cols-1)+b2;
01066                                 cv::line(depth_graph, cvPoint(depth_graph.cols-1,y), cvPoint((int)((x_left+2)*150),(int)(frame_left*100)), black, 5, 8, 0);
01067 
01068                                 jamb=1000;
01069                                 for(int k=depth_graph.cols-1; k>(x_left+2)*150; k--)
01070                                 {
01071                                         for(int m=1; m<depth_graph.rows-1; m++)
01072                                         {                               
01073                                                 if(depth_graph.data[m*depth_graph.cols+k]>0)
01074                                                 {
01075                                                         jamb=min(k,jamb);
01076                                                 }               
01077                                         }
01078                                 }
01079 
01080                                 door_x=(int)((b_c2.x+b_c3.x)/2)+50;
01081                                 for(int k=depth_graph.cols-1; k>door_x; k--)
01082                                 {
01083                                         if(!std::isnan(cloud.at(k,door_y).x) && !std::isnan(cloud.at(k,door_y).z) && cloud.at(k,door_y).z>0.0 && cloud.at(k,door_y).z<5.0)
01084                                         {
01085                                                 if(cloud.at(k,door_y).x > ((float)jamb/150)-2)
01086                                                 {
01087                                                         b_c2.x=k;
01088                                                         b_c3.x=k;
01089                                                         x_left=cloud.at(k,door_y).x;
01090                                                         min_depth=left_depth;
01091                                                         //cv::line(depth, cvPoint(k,door_y), cvPoint(k,door_y), black, 1, 8, 0);
01092                                                 }
01093                                         }
01094                                 }
01095                                 /*if (jamb==1000)
01096                                 {
01097                                         b_c2.x=depth.cols-1;
01098                                         b_c3.x=depth.cols-1;
01099                                 }*/
01100                                 //cv::line(original->image, cvPoint((int)((b_c2.x+b_c3.x)/2),door_y),cvPoint(right_door_end,door_y),white, 3, 8, 0);
01101                         }
01102 
01103                         for(int k=1; k<original->image.cols-1; k++)
01104                         {
01105                                 if(!std::isnan(cloud.at(k,door_y).x) && !std::isnan(cloud.at(k,door_y).z) && cloud.at(k,door_y).z>0.0 && cloud.at(k,door_y).z<5.0)
01106                                 {
01107                                         if(k<(int)((b_c1.x+b_c4.x)/2)-10) 
01108                                         {
01109                                                 x_right=cloud.at(k,door_y).x;
01110                                                 frame_right=cloud.at(k,door_y).z;
01111                                         }
01112                                 }
01113                         }
01114 
01115                         if(x<(x_right+2)*150)
01116                         {       
01117                                 door_end=left_door_end;
01118                                 side=-1;
01119                                 y = m1+b1;
01120                                 cv::line(depth_graph, cvPoint(1,y), cvPoint((int)((x_right+2)*150),(int)(frame_right*100)), black, 5, 8, 0);
01121 
01122                                 jamb=0;
01123                                 for(int k=1; k<(x_right+2)*150; k++)
01124                                 {
01125                                         for(int m=1; m<depth_graph.rows-1; m++)
01126                                         {                               
01127                                                 if(depth_graph.data[m*depth_graph.cols+k]>0)
01128                                                 {
01129                                                         jamb=max(k,jamb);
01130                                                 }               
01131                                         }
01132                                 }
01133 
01134                                 door_x=(int)((b_c1.x+b_c4.x)/2)-50;
01135                                 for(int k=1; k<door_x; k++)
01136                                 {
01137                                         if(!std::isnan(cloud.at(k,door_y).x) && !std::isnan(cloud.at(k,door_y).z) && cloud.at(k,door_y).z>0.0 && cloud.at(k,door_y).z<5.0)
01138                                         {
01139                                                 if(cloud.at(k,door_y).x < ((float)jamb/150)-2)
01140                                                 {
01141                                                         b_c1.x=k;
01142                                                         b_c4.x=k;
01143                                                         x_right=cloud.at(k,door_y).x;
01144                                                         min_depth=right_depth;
01145                                                         //cv::line(depth, cvPoint(k,door_y), cvPoint(k,door_y), black, 1, 8, 0);
01146                                                 }
01147                                         }
01148                                 }
01149                                 /*if (jamb==0)
01150                                 {
01151                                         b_c1.x=1;
01152                                         b_c4.x=1;
01153                                 }*/
01154                                 //cv::line(original->image, cvPoint((int)((b_c1.x+b_c4.x)/2),door_y),cvPoint(left_door_end,door_y),white, 3, 8, 0);
01155                         }
01156 
01157                         y = (m1*x)+b1;
01158                         cv::line(depth_graph, cvPoint(x,y), cvPoint(x,y), white, 10, 8, 0);
01159 
01160                         //cv::line(depth, cvPoint(x,frame_x), cvPoint(x,frame_x),white, 15, 8, 0);
01161                 
01162                         cx_min=min(min(b_c1.x,b_c2.x),min(b_c3.x,b_c4.x));
01163                         cx_max=max(max(b_c1.x,b_c2.x),max(b_c3.x,b_c4.x));
01164                         cy_min=min(min(b_c1.y,b_c2.y),min(b_c3.y,b_c4.y));
01165                         cy_max=max(max(b_c1.y,b_c2.y),max(b_c3.y,b_c4.y));
01166                 }
01167 
01168                 cv::Mat mask_image;
01169                 mask_image = cv::Mat::zeros(depth.rows, depth.cols, CV_8UC1);
01170                                                 
01171                 //Door area mask
01172                 DrawRect (mask_image, b_c1, b_c2, b_c3, b_c4, CV_RGB(100,100,100), 1, 1);
01173 
01174                 if (cx_min<0)                                           
01175                         cx_min=0;                       if (cx_max<4)
01176                                                                 cx_max=4;
01177                 if (cy_min<0)                                           
01178                         cy_min=0;                       if (cy_max<4)
01179                                                                 cy_max=4;
01180                 if (cx_min>original->image.cols-5)                                              
01181                         cx_min=original->image.cols-5;  if (cx_max>original->image.cols-1)
01182                                                                 cx_max=original->image.cols-1;
01183                 if (cy_min>original->image.rows-5)                                              
01184                         cy_min=original->image.rows-5;  if (cy_max>original->image.rows-1)
01185                                                                 cy_max=original->image.rows-1;
01186                 roi_x=abs(cx_max-cx_min);
01187                 roi_y=abs(cy_max-cy_min);
01188                 
01189                 //Aspect filter
01190                 aspect=0;       
01191                 r=roi_x/(roi_y+0.0001);
01192 
01193                 if(cx_min <= 10 || cx_max >= original->image.cols-10)
01194                         aspect = (r>=0.4 && r<=0.8);    
01195                 if(cy_min <= 10 || cy_max >= original->image.rows-10)
01196                         aspect = (r>=0.4 && r<=1.4);
01197                 if(cx_min >= 10 && cx_max <= original->image.cols-10 && cy_min >= 10 && cy_max <= original->image.rows-10)
01198                         aspect = (r>=0.4 && r<=0.8);
01199                 if((cx_min <= 10 || cx_max >= original->image.cols-10) && (cy_min <= 10 || cy_max >= original->image.rows-10))
01200                         aspect = (r>=0.4 && r<=1.4);
01201 
01202                 if(cx_min <= 10 || cx_max >= original->image.cols-10)
01203                         min_dst_h=min_dst_h/2;
01204                 if(cy_min <= 10 || cy_max >= original->image.rows-10)
01205                         min_dst_v=min_dst_v/3;
01206 
01207                 if(!Aspect_filter)
01208                         aspect=1;
01209 
01210                 //distance between corners
01211                 dst_up=sqrt((b_c2.x-b_c1.x)*(b_c2.x-b_c1.x)+(b_c2.y-b_c1.y)*(b_c2.y-b_c1.y));
01212                 dst_right=sqrt((b_c3.x-b_c2.x)*(b_c3.x-b_c2.x)+(b_c3.y-b_c2.y)*(b_c3.y-b_c2.y));
01213                 dst_down=sqrt((b_c4.x-b_c3.x)*(b_c4.x-b_c3.x)+(b_c4.y-b_c3.y)*(b_c4.y-b_c3.y));
01214                 dst_left=sqrt((b_c4.x-b_c1.x)*(b_c4.x-b_c1.x)+(b_c4.y-b_c1.y)*(b_c4.y-b_c1.y));
01215 
01216                 dst_h=(dst_down+dst_up)/2;
01217                 dst_v=(dst_left+dst_right)/2;
01218 
01219                 size = 0;
01220                 size = (dst_h>min_dst_h && dst_h<max_dst_h && dst_v>min_dst_v && dst_v<max_dst_v);
01221 
01222                 room_frame_height = abs(sill-lintel);
01223                 room_door_ratio = (float)room_frame_height/(float)roi_y;
01224 
01225                 if(aspect && size)
01226                 {
01227                         DrawRect (original->image, b_c1, b_c2, b_c3, b_c4, CV_RGB(0,0,255), 3, 0);
01228                         DrawRect (depth, b_c1, b_c2, b_c3, b_c4, CV_RGB(255,255,255), 3, 0);
01229 
01230                                 poses.pose.position.x = x_right;
01231                                 poses.pose.position.y = y_i;
01232                                 poses.pose.position.z = min_depth;
01233                 
01234                                 poses.pose.orientation.x = x_left;
01235                                 poses.pose.orientation.y = y_top;
01236                                 poses.pose.orientation.z = min_depth;
01237                                 poses.pose.orientation.w = side;        
01238 
01239                                 door_centroid_publisher_.publish(poses);
01240                         
01241                                 door_coordinates.data.clear();
01242                                 door_coordinates.data.push_back(b_c1.x);
01243                                 door_coordinates.data.push_back(b_c1.y);
01244                                 door_coordinates.data.push_back(b_c2.x);
01245                                 door_coordinates.data.push_back(b_c2.y);
01246                                 door_coordinates.data.push_back(b_c3.x);
01247                                 door_coordinates.data.push_back(b_c3.y);
01248                                 door_coordinates.data.push_back(b_c4.x);
01249                                 door_coordinates.data.push_back(b_c4.y);        
01250                                 door_coordinates.data.push_back(door_end);
01251                                 door_coordinates.data.push_back(side);
01252 
01253                                 open_door_coordinates_publisher_.publish(door_coordinates);
01254                 }       
01255         }
01256 
01257 
01258         if(debugging_images!=0)
01259         {
01260                 if(debugging_images==1)
01261                         cv::imshow(WINDOW_1, depth);
01262                 if(debugging_images==1)
01263                         cv::imshow(WINDOW_2, original->image);
01264                 //cv::imshow(WINDOW_2, depth_graph);
01265                 //cvMoveWindow(WINDOW_1, 0, 640);
01266                 cv::waitKey(3);  
01267         }
01268   }
01269   captured_depth = 0;  
01270 
01271   //unlock previously blocked shared variables 
01272   //this->alg_.unlock(); 
01273   this->points_mutex_.exit(); 
01274 }
01275 
01276 /*  [service callbacks] */
01277 
01278 /*  [action callbacks] */
01279 
01280 /*  [action requests] */
01281 
01282 void OpenDoorDetectorAlgNode::node_config_update(Config &config, uint32_t level)
01283 {
01284   this->alg_.lock();
01285 
01286         this->min_x = config.min_x;
01287         this->max_x = config.max_x;
01288         this->min_y = config.min_y;
01289         this->max_y = config.max_y;
01290         this->debugging_images = config.debugging_images;
01291         this->no_simulator = config.no_simulator;
01292         this->DSC = config.DSC;
01293         this->SVP = config.SVP;
01294         this->SVL = config.SVL;
01295         this->SFC = config.SFC;
01296         this->Range_filter = config.Range_filter;
01297         this->Persp_filter = config.Persp_filter;
01298         this->Geom_filter = config.Geom_filter ;
01299         this->Size_filter = config.Size_filter ;
01300         this->Aspect_filter = config.Aspect_filter;
01301         this->security_distance = config.security_distance;
01302 
01303   this->alg_.unlock();
01304 }
01305 
01306 void OpenDoorDetectorAlgNode::addNodeDiagnostics(void)
01307 {
01308 }
01309 
01310 /* main function */
01311 int main(int argc,char *argv[])
01312 {
01313   return algorithm_base::main<OpenDoorDetectorAlgNode>(argc, argv, "open_door_detector_alg_node");
01314 }
01315 
01316 /* other functions */
01317 void OpenDoorDetectorAlgNode::DoorSizeCalibration (cv::Mat inputImage, double min_dst_h, double max_dst_h, double min_dst_v, double max_dst_v)
01318 {       
01319 
01320         //Smallest door frame allowed
01321         c1= cvPoint((inputImage.cols/2)-(min_dst_h/2), (inputImage.rows/2)-(min_dst_v/2));
01322         c2= cvPoint((inputImage.cols/2)+(min_dst_h/2), (inputImage.rows/2)-(min_dst_v/2));
01323         c3= cvPoint((inputImage.cols/2)+(min_dst_h/2), (inputImage.rows/2)+(min_dst_v/2));
01324         c4= cvPoint((inputImage.cols/2)-(min_dst_h/2), (inputImage.rows/2)+(min_dst_v/2));
01325         
01326         DrawRect (inputImage, c1, c2, c3, c4, white, 2, 0);
01327 
01328         //Biggest door frame allowed
01329         c1= cvPoint((inputImage.cols/2)-(max_dst_h/2), (inputImage.rows/2)-(max_dst_v/2));
01330         c2= cvPoint((inputImage.cols/2)+(max_dst_h/2), (inputImage.rows/2)-(max_dst_v/2));
01331         c3= cvPoint((inputImage.cols/2)+(max_dst_h/2), (inputImage.rows/2)+(max_dst_v/2));
01332         c4= cvPoint((inputImage.cols/2)-(max_dst_h/2), (inputImage.rows/2)+(max_dst_v/2));
01333         
01334         DrawRect (inputImage, c1, c2, c3, c4, white, 2, 0);
01335 }
01336 
01337 void OpenDoorDetectorAlgNode::DrawRect (cv::Mat inputImage, cv::Point q1, cv::Point q2, cv::Point q3, cv::Point q4, cv::Scalar color, int lineSize, int filled)
01338 {       
01339         if(filled==0)
01340         {
01341                 cv::line(inputImage, q1, q2, color, lineSize);
01342                 cv::line(inputImage, q2, q3, color, lineSize);
01343                 cv::line(inputImage, q3, q4, color, lineSize);
01344                 cv::line(inputImage, q4, q1, color, lineSize);
01345         }
01346 
01347         if(filled==1)
01348         {
01349                 std::vector<cv::Point> pts;
01350                 pts.push_back(q1);
01351                 pts.push_back(q2);
01352                 pts.push_back(q3);
01353                 pts.push_back(q4);
01354         
01355                 cv::Point *pP = new cv::Point[pts.size()];
01356                 std::copy(pts.begin(), pts.end(), pP);
01357                 fillConvexPoly(inputImage, pP, 4, color);
01358         }
01359 }
01360 
01361 double OpenDoorDetectorAlgNode::AngleBetweenLines (cv::Point point1, cv::Point point2, cv::Point point3, cv::Point point4)
01362 {       
01363         double m1, m2, dx, dy;
01364 
01365         dy=point2.y-point1.y;
01366         dx=point2.y-point1.y;
01367         m1=dy/(dx+0.0001);
01368         dy=point4.y-point3.y;
01369         dx=point4.x-point3.x;
01370         m2=dy/(dx+0.0001);
01371 
01372         double theta=atan(abs((m2-m1)/(1.0001+m1*m2)));
01373         
01374         return theta;
01375 }
01376 


iri_door_detector
Author(s): Jose Rodriguez
autogenerated on Fri Dec 6 2013 23:57:16