Subscriber.cpp
Go to the documentation of this file.
00001 /******************************************************************************
00002  * Copyright (C) 2014 by Ralf Kaestner                                        *
00003  * ralf.kaestner@gmail.com                                                    *
00004  *                                                                            *
00005  * This program is free software; you can redistribute it and/or modify       *
00006  * it under the terms of the Lesser GNU General Public License as published by*
00007  * the Free Software Foundation; either version 3 of the License, or          *
00008  * (at your option) any later version.                                        *
00009  *                                                                            *
00010  * This program is distributed in the hope that it will be useful,            *
00011  * but WITHOUT ANY WARRANTY; without even the implied warranty of             *
00012  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the               *
00013  * Lesser GNU General Public License for more details.                        *
00014  *                                                                            *
00015  * You should have received a copy of the Lesser GNU General Public License   *
00016  * along with this program. If not, see <http://www.gnu.org/licenses/>.       *
00017  ******************************************************************************/
00018 
00019 #include "variant_topic_tools/DataTypeRegistry.h"
00020 #include "variant_topic_tools/Exceptions.h"
00021 #include "variant_topic_tools/Message.h"
00022 #include "variant_topic_tools/Subscriber.h"
00023 
00024 namespace variant_topic_tools {
00025 
00026 /*****************************************************************************/
00027 /* Constructors and Destructor                                               */
00028 /*****************************************************************************/
00029 
00030 Subscriber::Subscriber() {
00031 }
00032 
00033 Subscriber::Subscriber(const Subscriber& src) :
00034   impl(src.impl) {
00035 }
00036 
00037 Subscriber::~Subscriber() {  
00038 }
00039 
00040 Subscriber::Impl::Impl(ros::NodeHandle& nodeHandle, const MessageType& type,
00041     const std::string& topic, size_t queueSize, const SubscriberCallback&
00042     callback) :
00043   type(type),
00044   callback(callback) {
00045   subscriber = nodeHandle.subscribe(topic, queueSize,
00046     &Subscriber::Impl::eventCallback, this);
00047 }
00048 
00049 Subscriber::Impl::~Impl() {
00050   shutdown();
00051 }
00052 
00053 /*****************************************************************************/
00054 /* Operators                                                                 */
00055 /*****************************************************************************/
00056 
00057 Subscriber::operator ros::Subscriber() const {
00058   if (impl)
00059     return impl->subscriber;
00060   else
00061     return ros::Subscriber();
00062 }
00063 
00064 /*****************************************************************************/
00065 /* Accessors                                                                 */
00066 /*****************************************************************************/
00067 
00068 std::string Subscriber::getTopic() const {
00069   if (impl)
00070     return impl->subscriber.getTopic();
00071   else
00072     return std::string();
00073 }
00074 
00075 size_t Subscriber::getNumPublishers() const {
00076   if (impl)
00077     return impl->subscriber.getNumPublishers();
00078   else
00079     return 0;
00080 }
00081 
00082 bool Subscriber::Impl::isValid() const {
00083   return subscriber;
00084 }
00085 
00086 /*****************************************************************************/
00087 /* Methods                                                                   */
00088 /*****************************************************************************/
00089 
00090 void Subscriber::shutdown() {
00091   if (impl)
00092     impl->shutdown();
00093 }
00094 
00095 void Subscriber::Impl::shutdown() {
00096   subscriber = ros::Subscriber();
00097   
00098   type = MessageType();
00099   dataType = DataType();
00100   serializer = MessageSerializer();
00101 }
00102 
00103 void Subscriber::Impl::eventCallback(const ros::MessageEvent<Message const>&
00104     event) {
00105   boost::shared_ptr<const Message> message = event.getConstMessage();
00106   
00107   if (!type.isValid())
00108     type = message->getType();
00109   
00110   if (message->getType().getDataType() == type.getDataType()) {
00111     if ((type.getMD5Sum() == "*") || (message->getType().getMD5Sum() == "*") ||
00112         (message->getType().getMD5Sum() == type.getMD5Sum())) {
00113       if (!dataType) {
00114         DataTypeRegistry registry;
00115         dataType = registry.getDataType(type.getDataType());
00116         
00117         if (!dataType) {
00118           type = message->getType();
00119           
00120           MessageDefinition definition(type);
00121           dataType = definition.getMessageDataType();
00122         }
00123       }
00124         
00125       if (dataType && !serializer)
00126         serializer = dataType.createSerializer();
00127 
00128       if (serializer) {
00129         MessageVariant variant = dataType.createVariant();
00130         ros::serialization::IStream stream(const_cast<uint8_t*>(
00131           message->getData().data()), message->getSize());
00132         
00133         serializer.deserialize(stream, variant);
00134         
00135         callback(variant, event.getReceiptTime());
00136       }
00137     }
00138     else
00139       throw MD5SumMismatchException(type.getMD5Sum(),
00140         message->getType().getMD5Sum());
00141   }
00142   else
00143     throw MessageTypeMismatchException(type.getDataType(),
00144       message->getType().getDataType());
00145 }
00146 
00147 }


variant_topic_tools
Author(s): Ralf Kaestner
autogenerated on Tue Jul 9 2019 03:18:42