odor_bar.cpp
Go to the documentation of this file.
00001 /*********************************************************************
00002 *
00003 * Software License Agreement (BSD License)
00004 *
00005 *  Copyright (c) 2010, ISR University of Coimbra.
00006 *  All rights reserved.
00007 *
00008 *  Redistribution and use in source and binary forms, with or without
00009 *  modification, are permitted provided that the following conditions
00010 *  are met:
00011 *
00012 *   * Redistributions of source code must retain the above copyright
00013 *     notice, this list of conditions and the following disclaimer.
00014 *   * Redistributions in binary form must reproduce the above
00015 *     copyright notice, this list of conditions and the following
00016 *     disclaimer in the documentation and/or other materials provided
00017 *     with the distribution.
00018 *   * Neither the name of the ISR University of Coimbra nor the names of its
00019 *     contributors may be used to endorse or promote products derived
00020 *     from this software without specific prior written permission.
00021 *
00022 *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
00023 *  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
00024 *  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
00025 *  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
00026 *  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
00027 *  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
00028 *  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
00029 *  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
00030 *  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
00031 *  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
00032 *  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
00033 *  POSSIBILITY OF SUCH DAMAGE.
00034 *
00035 * Author: Pedro Sousa on 27/08/2010
00036 *********************************************************************/
00037 #include <ros/ros.h>
00038 #include <visualization_msgs/Marker.h>
00039 #include <std_msgs/ColorRGBA.h>
00040 #include <lse_sensor_msgs/Nostril.h>
00041 #include <lse_sensor_msgs/TPA.h>
00042 
00043 #define NODE_VERSION 0.2
00044 
00045 #define PIXEL_TO_M 20.0
00046 
00047 
00049 bool verbose = true;
00050 
00051 //nav_msgs::Odometry myOdom;
00053 double hsvS = 1.0, hsvV = 1.0;
00054 int hueMax = 200, hueMin = 0;
00055 
00057 // TODO: change this for something better
00058 lse_sensor_msgs::Nostril myNostril, myNostril_0, myNostril_1;
00059 
00060 
00061 void noseCallback(const lse_sensor_msgs::NostrilConstPtr& msg)
00062 {
00063         myNostril.sensor_model = msg->sensor_model;
00064         if(myNostril.sensor_model.compare("Figaro 2620"))
00065         {
00066                 myNostril_0.sensor_model = msg->sensor_model;
00067                 myNostril_0.reading = msg->reading;
00068         }
00069         else if(myNostril.sensor_model.compare("Figaro 2600"))
00070         {
00071                 myNostril_1.sensor_model = msg->sensor_model;
00072                 myNostril_1.reading = msg->reading;
00073         }
00074 
00075         //ROS_INFO("NoseCallback: <0>%s:%f   <1>%s:%f", myNostril_0.sensor_model.c_str(), myNostril_0.reading, myNostril_1.sensor_model.c_str(), myNostril_1.reading);
00076 
00077 }
00078 
00079 
00086 std::string char2string(char *in)
00087 {
00088     std::string str(in);
00089     return str;
00090 }
00091 
00092 
00093 
00103 std_msgs::ColorRGBA hsv_2_rgb(float H, float S, float V)
00104 {
00105         float R, G, B;
00106         double hf;
00107         int    i;
00108         double f;
00109         double pv;
00110         double qv;
00111         double tv;
00112         
00113         std_msgs::ColorRGBA rgbColor;
00114         
00115         // h -> [0...360]
00116         // s and v -> [0...1]
00117         if( V == 0 )
00118         {
00119                 R = 0;
00120                 G = 0;
00121                 B = 0;
00122         }
00123         else if( S == 0 )
00124         {
00125                 R = V;
00126                 G = V;
00127                 B = V;
00128         }
00129         else
00130         {
00131                 hf = H / 60.0;
00132                 i  = (int) floor( hf );
00133                 f  = hf - i;
00134                 pv  = V * ( 1 - S );
00135                 qv  = V * ( 1 - S * f );
00136                 tv  = V * ( 1 - S * ( 1 - f ) );
00137                 //ROS_INFO("i%d",i);
00138                 switch( i )
00139                 {
00140                         // Red is the dominant color
00141                         case 0:
00142                                 R = V;
00143                                 G = tv;
00144                                 B = pv;
00145                                 break;
00146                         // Green is the dominant color
00147                         
00148                         case 1:
00149                                 R = qv;
00150                                 G = V;
00151                                 B = pv;
00152                                 break;
00153                         case 2:
00154                                 R = pv;
00155                                 G = V;
00156                                 B = tv;
00157                                 break;
00158                         // Blue is the dominant color
00159                         case 3:
00160                                 R = pv;
00161                                 G = qv;
00162                                 B = V;
00163                                 break;
00164                         case 4:
00165                                 R = tv;
00166                                 G = pv;
00167                                 B = V;
00168                                 break;
00169                         // Red is the dominant color
00170                         case 5:
00171                           R = V;
00172                           G = pv;
00173                           B = qv;
00174                           break;
00175                         // just in case something goes wrong 
00176                         case 6:
00177                                 R = V;
00178                                 G = tv;
00179                                 B = pv;
00180                                 break;
00181                         case -1:
00182                                 R = V;
00183                                 G = pv;
00184                                 B = qv;
00185                                 break;
00186                         default:
00187                                 // shouldn't get here
00188                                 ROS_ERROR("Value error in Pixel conversion...,");
00189                                 break;
00190                 }
00191         }
00192         // RGB values from 0...1
00193         rgbColor.r = R;
00194         rgbColor.g = G;
00195         rgbColor.b = B;
00196         
00197         return rgbColor;
00198 }
00199 
00200 
00209 void makeColorBar(visualization_msgs::Marker *ptrMarker, int val)
00210 {
00211         std_msgs::ColorRGBA col;
00212         int step;
00213         int N_STEPS = 10;
00214         float v;
00215         int idx = 0;
00216         int deltaHue;
00217         
00218         deltaHue = hueMax - hueMin;
00219 
00220         step = deltaHue / N_STEPS;
00221         //val = val * 6;
00222         val = (val <= 100) ? val : 100;
00223         //ROS_INFO("val:%d", val);
00224         v = (val/100.0) * deltaHue;
00225         
00226         // clear current values
00227         ptrMarker->points.clear();
00228         ptrMarker->colors.clear();
00229         
00230         // Fill in the colors
00231         for (int j = deltaHue; j > (deltaHue - v);j = j - step)
00232         {
00233                 col = hsv_2_rgb(j, hsvS, hsvV);
00234                 ptrMarker->colors.push_back(col);
00235                 idx++;
00236         }
00237         // And now the objects
00238         for (int i = 0; i < idx;i++)
00239         {
00240                 geometry_msgs::Point p;
00241                 p.x = 0.0;
00242                 p.y = -0.3;
00243                 p.z = (0.2 + (i*0.15));
00244                 
00245                 // add point to vector
00246                 ptrMarker->points.push_back(p);
00247         }
00248         //ROS_INFO("step:%d  v:%f", step, v);   
00249 }
00250 
00251 
00252 void configColorBar(ros::NodeHandle *pn, visualization_msgs::Marker *ptrMarker)
00253 {
00254         // Read parameters
00255         // Scale
00256         pn->param("scale/x", ptrMarker->scale.x, 0.15);
00257         pn->param("scale/y", ptrMarker->scale.x, 0.15);
00258         pn->param("scale/z", ptrMarker->scale.x, 0.15);
00259 
00260         // HSV S and V components
00261         pn->param("hsv_s", hsvS, 1.0);
00262         pn->param("hsv_v", hsvV, 1.0);
00263 
00264         // HSV H interval
00265         pn->param("hue_max", hueMax, 200);
00266         pn->param("hue_min", hueMin, 0);
00267 }
00268 
00269 
00270 int main( int argc, char** argv )
00271 {
00272         ros::init(argc, argv, "odor_bar");
00273         ros::NodeHandle n("~");
00274         ROS_INFO("odor_bar for ROS %.2f", NODE_VERSION);
00275 
00276         ros::Subscriber nose_sub = n.subscribe("nose", 2, noseCallback);
00277 
00278         ros::Publisher marker_pub = n.advertise<visualization_msgs::Marker>("odor_bars", 10);
00279 
00280         float chem_val = 0;
00281         char currValue[5];
00282         
00283 
00284         ros::Rate r(1);
00285 
00286         while (ros::ok())
00287         {
00288                 visualization_msgs::Marker points, text;
00289                 points.header.frame_id = text.header.frame_id = "/base_link";
00290                 points.header.stamp = text.header.stamp = ros::Time::now();
00291                 points.ns = text.ns = "odor_bar";
00292                 text.lifetime = ros::Duration();
00293                 points.action = text.action = visualization_msgs::Marker::ADD;
00294                 points.pose.orientation.w = text.pose.orientation.w = 1.0;
00295 
00296 
00297                 points.id = 0;
00298                 text.id = 1;
00299 
00300 
00301                 points.type = visualization_msgs::Marker::CUBE_LIST;
00302                 text.type = visualization_msgs::Marker::TEXT_VIEW_FACING;
00303 
00304 
00305                 // POINTS markers use x and y scale for width/height respectively
00306                 points.scale.x = 0.15;
00307                 points.scale.y = 0.15;
00308                 points.scale.z = 0.15;
00309 
00310                 // LINE_STRIP/LINE_LIST markers use only the x component of scale, for the line width
00311                 text.scale.z = 0.1;
00312 
00313 
00314 
00315                 // Points are green
00316                 points.color.g = 1.0f;
00317                 points.color.a = 1.0;
00318 
00319                 // Line list is red
00320                 text.color.r = 1.0;
00321                 text.color.a = 1.0;
00322 
00323 
00324                 geometry_msgs::Point p;
00325                 p.x = 0;
00326                 p.y = 0.1;
00327                 p.z = 0.5;
00328                 text.points.push_back(p);
00329 
00330 
00331                 chem_val = myNostril_0.reading;
00332                 //ROS_INFO("val:%f", chem_val);
00333                 chem_val = (100.0/3000.0) * chem_val;
00334                 //ROS_INFO("norm_val:%f", chem_val);
00335                 makeColorBar(&points, (int)(chem_val)); 
00336 
00337                 sprintf(currValue,"%d%%", (int)chem_val);
00338                 //ROS_INFO("currValue:%s", currValue);
00339                 text.text.clear();
00340                 text.text = currValue;
00341                 marker_pub.publish(text);
00342 
00343                 marker_pub.publish(points);
00344 
00345    
00346                 ros::spinOnce();
00347                 r.sleep();
00348         }
00349 
00350         ROS_INFO("That's enough!!!");
00351 }
00352 
00353 
00354 
00355 
00356 


odor_bar
Author(s): Pedro Sousa
autogenerated on Mon Jan 6 2014 11:27:27