00001
00002
00003
00004
00005 #include "ros/ros.h"
00006 #include "std_msgs/Bool.h"
00007 #include "sensor_msgs/Range.h"
00008
00009 #include <libphidgets/phidget21.h>
00010 #include <sstream>
00011
00012 class Sensor
00013 {
00014 ros::NodeHandle n_;
00015 ros::Publisher pub_range_;
00016 int id_, filter_size_;
00017 std::list<int> vals_;
00018 std::string frame_id_;
00019 public:
00020
00021 Sensor(const std::string &fr_id, const int id, const int filter_size = 10) :
00022 id_(id), filter_size_(filter_size), frame_id_(fr_id)
00023 {
00024 char buffer[256];
00025 sprintf(buffer, "range_%d", id);
00026 pub_range_ = n_.advertise<sensor_msgs::Range>(buffer, 0);
00027 }
00028
00029 void publish()
00030 {
00031 pub_range_.publish((sensor_msgs::Range) *this);
00032 }
00033
00034 operator sensor_msgs::Range() const
00035 {
00036 sensor_msgs::Range msg;
00037 msg.header.stamp = ros::Time::now();
00038 msg.header.frame_id = frame_id_;
00039 msg.radiation_type = sensor_msgs::Range::INFRARED;
00040 msg.min_range = 0.04;
00041 msg.max_range = 0.3;
00042 msg.field_of_view = 0;
00043
00044 int sum = 0, num = 0;
00045 for (std::list<int>::const_iterator it = vals_.begin();
00046 it != vals_.end(); it++)
00047 {
00048 sum += *it;
00049 ++num;
00050 }
00051 msg.range = 20.76 / (sum / (double) num - 11.);
00052
00053 return msg;
00054 }
00055
00056 int getId() const
00057 {
00058 return id_;
00059 }
00060
00061 void update(const int v)
00062 {
00063 if ((int)vals_.size() < filter_size_)
00064 vals_.push_back(v);
00065 else
00066 {
00067 vals_.push_back(v);
00068 vals_.pop_front();
00069 }
00070 }
00071
00072 };
00073
00074 void display_generic_properties(CPhidgetHandle phid)
00075 {
00076 int sernum, version;
00077 const char *deviceptr, *label;
00078 CPhidget_getDeviceType(phid, &deviceptr);
00079 CPhidget_getSerialNumber(phid, &sernum);
00080 CPhidget_getDeviceVersion(phid, &version);
00081 CPhidget_getDeviceLabel(phid, &label);
00082
00083 ROS_INFO("%s", deviceptr);
00084 ROS_INFO("Version: %8d SerialNumber: %10d", version, sernum);
00085 ROS_INFO("Label: %s", label);
00086 return;
00087 }
00088
00089 int IFK_AttachHandler(CPhidgetHandle IFK, void *userptr)
00090 {
00091
00092
00093 return 0;
00094 }
00095
00096 int IFK_SensorChangeHandler(CPhidgetInterfaceKitHandle IFK, void *userptr,
00097 int Index, int Value)
00098 {
00099 std::vector<Sensor>* g_sensors = (std::vector<Sensor>*) userptr;
00100 for (size_t i = 0; i < g_sensors->size(); i++)
00101 if ((*g_sensors)[i].getId() == Index)
00102 (*g_sensors)[i].update(Value);
00103 return 0;
00104 }
00105
00106 int main(int argc, char **argv)
00107 {
00108 ros::init(argc, argv, "cob_phidgets");
00109
00110 ros::NodeHandle nh_("~");
00111 std::vector<Sensor> g_sensors;
00112 if (nh_.hasParam("sensors"))
00113 {
00114 XmlRpc::XmlRpcValue v;
00115 nh_.param("sensors", v, v);
00116 for (int i = 0; i < v.size(); i++)
00117 {
00118 ROS_ASSERT(v[i].size()>=2);
00119
00120 int id = v[i][0];
00121 std::string fr_id = v[i][1];
00122 int filter = v.size() > 2 ? (int) v[i][2] : 10;
00123
00124 g_sensors.push_back(Sensor(fr_id, id, filter));
00125 }
00126 }
00127 else
00128 {
00129 ROS_ERROR("Parameter sensors not set, shutting down node...");
00130 nh_.shutdown();
00131 return false;
00132 }
00133
00134 ros::Rate loop_rate(10);
00135
00136
00137 int numInputs, numOutputs, numSensors;
00138 int err;
00139
00140 CPhidgetInterfaceKitHandle IFK = 0;
00141 CPhidget_enableLogging(PHIDGET_LOG_VERBOSE, NULL);
00142 CPhidgetInterfaceKit_create(&IFK);
00143 CPhidgetInterfaceKit_set_OnSensorChange_Handler(IFK,
00144 IFK_SensorChangeHandler, (void*) &g_sensors);
00145 CPhidget_set_OnAttach_Handler((CPhidgetHandle) IFK, IFK_AttachHandler,
00146 NULL);
00147
00148 CPhidget_open((CPhidgetHandle) IFK, -1);
00149
00150
00151 ROS_INFO("waiting for phidgets attachement...");
00152 if ((err = CPhidget_waitForAttachment((CPhidgetHandle) IFK, 10000))
00153 != EPHIDGET_OK)
00154 {
00155 const char *errStr;
00156 CPhidget_getErrorDescription(err, &errStr);
00157 ROS_ERROR("Error waiting for attachment: (%d): %s", err, errStr);
00158 goto exit;
00159 }
00160 ROS_INFO("... attached");
00161
00162 display_generic_properties((CPhidgetHandle) IFK);
00163 CPhidgetInterfaceKit_getOutputCount((CPhidgetInterfaceKitHandle) IFK,
00164 &numOutputs);
00165 CPhidgetInterfaceKit_getInputCount((CPhidgetInterfaceKitHandle) IFK,
00166 &numInputs);
00167 CPhidgetInterfaceKit_getSensorCount((CPhidgetInterfaceKitHandle) IFK,
00168 &numSensors);
00169
00170
00171 ROS_INFO(
00172 "Sensors:%d Inputs:%d Outputs:%d", numSensors, numInputs, numOutputs);
00173
00174 while (ros::ok())
00175 {
00176 for (size_t i = 0; i < g_sensors.size(); i++)
00177 g_sensors[i].publish();
00178 ros::spinOnce();
00179 loop_rate.sleep();
00180 }
00181
00182 exit: CPhidget_close((CPhidgetHandle) IFK);
00183 CPhidget_delete((CPhidgetHandle) IFK);
00184
00185 return 0;
00186 }