commit 93cebb998b81dc98f54dac5728560ecc511c7224
Author: Yuyang (Misty) Guo <yuyangg@andrew.cmu.edu>
Date:   Sun Nov 3 16:02:08 2013 -0500

    added BomControl class and to the scout sensor

diff --git a/scout/libscout/src/Behavior.cpp b/scout/libscout/src/Behavior.cpp
index d58ab78..d696c06 100644
--- a/scout/libscout/src/Behavior.cpp
+++ b/scout/libscout/src/Behavior.cpp
@@ -60,7 +60,8 @@ Behavior::Behavior(string scoutname, string my_name, Sensors * sensors)
     name = my_name;
     keep_running = true;
     sensors->init(&motors, &buttons, &sonar, &encoders, &linesensor,
-                        &wl_sender, &wl_receiver, &paintboard, &metal_detector);
+                  &wl_sender, &wl_receiver, &paintboard, &metal_detector,
+                  &bom);
     wl_receiver->register_callback(std::bind(&Behavior::default_callback,
         this, std::placeholders::_1));
 
diff --git a/scout/libscout/src/Behavior.h b/scout/libscout/src/Behavior.h
index 03ad47c..6a60c6a 100644
--- a/scout/libscout/src/Behavior.h
+++ b/scout/libscout/src/Behavior.h
@@ -94,6 +94,7 @@ class Behavior
         WirelessReceiver * wl_receiver;
         PaintBoardControl * paintboard;
         MetalDetectorControl * metal_detector;
+        BomControl * bom;
 
         // Default callback for wireless receiver.
         void default_callback(std::vector<uint8_t> data);
diff --git a/scout/libscout/src/BomControl.cpp b/scout/libscout/src/BomControl.cpp
new file mode 100644
index 0000000..27c6839
--- /dev/null
+++ b/scout/libscout/src/BomControl.cpp
@@ -0,0 +1,65 @@
+/**
+ * Copyright (c) 2011 Colony Project
+ * 
+ * Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use,
+ * copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following
+ * conditions:
+ * 
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ * 
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
+ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+ * OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+/**
+ * @file BomControl.h
+ * @brief Contains line follwing sensor declarations and functions
+ *
+ * @author Colony Project, CMU Robotics Club
+ * @author Yuyang (Misty) Guo
+ */
+
+ #include "BomControl.h"
+
+ using namespace std;
+
+/**
+ * @brief Initialize the BOM module of libscout.
+ */
+BomControl::BomControl(const ros::NodeHandle& libscout_node, string scoutname)
+    : node(libscout_node)
+{
+    query_client =
+        node.serviceClient< ::messages::query_boms>(scoutname+"/query_boms");
+}
+
+vector<uint32_t> BomControl::query()
+{
+    ::messages::query_boms srv;
+
+    if (!query_client.call(srv))
+    {
+        ROS_ERROR("BOM_Control query failed.");
+    }
+
+    if (srv.response.readings.size() != 10)
+    {
+        ROS_WARN("BOM_Control reading vector has %d readings, 10 expected.",
+                 int(srv.response.readings.size()));
+    }
+
+    return srv.response.readings;
+}
+
diff --git a/scout/libscout/src/BomControl.h b/scout/libscout/src/BomControl.h
new file mode 100644
index 0000000..45ab7e1
--- /dev/null
+++ b/scout/libscout/src/BomControl.h
@@ -0,0 +1,60 @@
+/**
+ * Copyright (c) 2011 Colony Project
+ * 
+ * Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use,
+ * copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following
+ * conditions:
+ * 
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ * 
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
+ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+ * OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+/**
+ * @file BomControl.h
+ * @brief Contains line follwing sensor declarations and functions
+ *
+ * @author Colony Project, CMU Robotics Club
+ * @author Yuyang (Misty) Guo
+ */
+
+#ifndef _BOM_CONTROL_H_
+#define _BOM_CONTROL_H_
+
+#include <ros/ros.h>
+#include <messages/query_boms.h>
+
+class BomControl
+{
+    public:
+        /** Set up the encoders class and prepare to communicate over ROS */
+        BomControl(const ros::NodeHandle& libscout_node,
+                          std::string scoutname);
+
+        /** Use ROS to get the current readings. */
+        std::vector<uint32_t> query();;
+
+        /**  */
+        //std::double getSourceEstimation();
+
+    private:
+        /* ROS publisher and client declaration */
+        ros::ServiceClient query_client;
+        ros::NodeHandle node;
+};
+
+#endif /* _BOM_CONTORL_H_ */
+
diff --git a/scout/libscout/src/Sensors.cpp b/scout/libscout/src/Sensors.cpp
index 0fc8dff..2f8bcc7 100644
--- a/scout/libscout/src/Sensors.cpp
+++ b/scout/libscout/src/Sensors.cpp
@@ -50,6 +50,7 @@ Sensors::Sensors(string scoutname)
     wl_sender = new WirelessSender(node);
     paintboard = new PaintBoardControl(node, scoutname);
     metal_detector = new MetalDetectorControl(node, scoutname);
+    bom = new BomControl(node, scoutname);
 }
 
 // b_stuff stand for behavior control class
@@ -59,7 +60,8 @@ void Sensors::init(MotorControl** b_motors, ButtonControl ** b_buttons,
                   WirelessSender ** b_wl_sender,
                   WirelessReceiver ** b_wl_receiver,
                   PaintBoardControl ** b_paintboard,
-                  MetalDetectorControl ** b_metal_detector)
+                  MetalDetectorControl ** b_metal_detector,
+                  BomControl ** b_bom)
 {
     //(MotorControl *)(* b_motors) = motors;
     *b_motors = motors;
@@ -71,4 +73,5 @@ void Sensors::init(MotorControl** b_motors, ButtonControl ** b_buttons,
     *b_wl_receiver = new WirelessReceiver(node);
     *b_paintboard = paintboard;
     *b_metal_detector = metal_detector;
+    *b_bom = bom;
 }
diff --git a/scout/libscout/src/Sensors.h b/scout/libscout/src/Sensors.h
index 6ac770e..7fd617b 100644
--- a/scout/libscout/src/Sensors.h
+++ b/scout/libscout/src/Sensors.h
@@ -43,6 +43,7 @@
 #include "MotorControl.h"
 #include "HeadlightControl.h"
 #include "ButtonControl.h"
+#include "BomControl.h"
 #include "SonarControl.h"
 //#include "CliffsensorControl.h"
 #include "EncodersControl.h"
@@ -63,7 +64,9 @@ class Sensors
                   WirelessSender ** b_wl_sender,
                   WirelessReceiver ** b_wl_receiver,
                   PaintBoardControl ** b_paintboard,
-                  MetalDetectorControl ** b_metal_detector);
+                  MetalDetectorControl ** b_metal_detector,
+                  BomControl ** b_bom
+                  );
         std::string name;
     private:
         ros::NodeHandle node;
@@ -77,6 +80,7 @@ class Sensors
         WirelessReceiver * wl_receiver;
         PaintBoardControl * paintboard;
         MetalDetectorControl * metal_detector;
+        BomControl * bom;
 };
 
 
diff --git a/scout/messages/srv/query_boms.srv b/scout/messages/srv/query_boms.srv
index 7bf2041..7f90a9f 100644
--- a/scout/messages/srv/query_boms.srv
+++ b/scout/messages/srv/query_boms.srv
@@ -1,4 +1,4 @@
 ---
 # All units are simply in encoder ticks since encoders were turned
 uint32[] readings
-int8[] senders
+uint32[] senders
diff --git a/scout/scoutsim/src/scout.cpp b/scout/scoutsim/src/scout.cpp
index 47b8965..a580827 100644
--- a/scout/scoutsim/src/scout.cpp
+++ b/scout/scoutsim/src/scout.cpp
@@ -121,11 +121,23 @@ namespace scoutsim
                                   &Scout::query_linesensor_callback,
                                   this);
 
+        query_BOM_srv =
+            node.advertiseService("query_BOM",
+                                  &Scout::query_BOM_callback,
+                                  this);
+
+
         for (unsigned int i = 0; i < NUM_LINESENSORS; i++)
         {
             linesensor_readings.push_back(0);
         }
 
+        for (unsigned int i = 0; i < NUM_BOMS; i++)
+        {
+            BOM_readings.push_back(0);
+            BOM_senders.push_back(0);
+        }
+
         // Initialize sonar
         sonar_position = 0;
         sonar_stop_l = 0;
@@ -276,6 +288,15 @@ namespace scoutsim
         return true;
     }
 
+    bool Scout::query_BOM_callback(::messages::query_boms::Request&,
+                                   ::messages::query_boms::Response& res)
+    {
+        res.readings = BOM_readings;
+        res.senders = BOM_senders;
+
+        return true;
+    }
+
     // Scale to linesensor value
     unsigned int Scout::rgb_to_grey(unsigned char r,
                                     unsigned char g,
@@ -429,11 +450,14 @@ namespace scoutsim
         }
     }
 
-    void Scout::update_BOM(int bom_index, bool bom_value) {
+    void Scout::update_BOM(int bom_index,
+                           unsigned int bom_value,
+                           unsigned int sender) {
         ROS_INFO("BOM%d: %d", bom_index, bom_value);
+        BOM_readings[bom_index] = bom_value;
+        BOM_senders[bom_index] = sender;
     }
 
-
     /// Sends back the position of this scout so scoutsim can save
     /// the world state
     /// @todo remove dt param
diff --git a/scout/scoutsim/src/scout.h b/scout/scoutsim/src/scout.h
index 5b6119d..491354f 100644
--- a/scout/scoutsim/src/scout.h
+++ b/scout/scoutsim/src/scout.h
@@ -55,6 +55,7 @@
 #include <messages/set_motors.h>
 #include <messages/query_encoders.h>
 #include <messages/query_linesensor.h>
+#include <messages/query_boms.h>
 #include <messages/sonar_distance.h>
 #include <messages/sonar_toggle.h>
 #include <messages/sonar_set_scan.h>
@@ -73,6 +74,7 @@
 #define PI 3.14159265
 
 #define NUM_LINESENSORS 8
+#define NUM_BOMS 10
 
 // Distance, pixels, from center of robot to the linesensors.
 #define LNSNSR_D 20
@@ -121,7 +123,8 @@ namespace scoutsim
                                          world_state state);
             void paint(wxDC& dc);
             void set_sonar_visual(bool on);
-            void update_BOM(int bom_index,bool bom_value);
+            void update_BOM(int bom_index, unsigned int bom_value,
+                            unsigned int sender);
 
         private:
             float absolute_to_mps(int absolute_speed);
@@ -132,6 +135,8 @@ namespace scoutsim
                                      messages::query_encoders::Response&);
             bool query_linesensor_callback(messages::query_linesensor::Request&,
                                      messages::query_linesensor::Response&);
+            bool query_BOM_callback(messages::query_boms::Request&,
+                                     messages::query_boms::Response&);
             bool handle_sonar_toggle(messages::sonar_toggle::Request  &req,
                                      messages::sonar_toggle::Response &res);
             bool handle_sonar_set_scan(messages::sonar_set_scan::Request  &req,
@@ -147,6 +152,7 @@ namespace scoutsim
                               double robot_theta, wxMemoryDC& sonar_dc);
             void update_linesensor(const wxImage& lines_image, int x, int y,
                                    double theta);
+
             int old_front_dx;
             int old_front_dy;
             int old_back_dx;
@@ -196,6 +202,8 @@ namespace scoutsim
 
             // A vector of the 8 linesensor readings
             std::vector<unsigned int> linesensor_readings;
+            std::vector<unsigned int> BOM_readings;
+            std::vector<unsigned int> BOM_senders;
 
             // Each scout has a unique id number, which is also displayed on its image.
             int scout_id;
@@ -211,6 +219,7 @@ namespace scoutsim
             ros::ServiceServer set_pen_srv;
             ros::ServiceServer query_encoders_srv;
             ros::ServiceServer query_linesensor_srv;
+            ros::ServiceServer query_BOM_srv;
             ros::ServiceServer toggle_sonar_srv;
             ros::ServiceServer set_sonar_srv;
 
diff --git a/scout/scoutsim/src/sim_frame.cpp b/scout/scoutsim/src/sim_frame.cpp
index ca80e14..f490931 100644
--- a/scout/scoutsim/src/sim_frame.cpp
+++ b/scout/scoutsim/src/sim_frame.cpp
@@ -786,12 +786,14 @@ namespace scoutsim
 
                 if(is_inrange(emitter_pos, bom_pos, bom_aperture, bom_distance)) {
                         
-                        it->second->update_BOM(i, true);
+                        it->second->update_BOM(i, 1, 0);
+                            // TODO: change to last arg to actual sender ID
                         
                     }
                 else {
                         
-                        it->second->update_BOM(i, false);
+                        it->second->update_BOM(i, 1, 0);
+                            // TODO: change to last arg to actual sender ID
                         
                 }
                 }
