NTRT Simulator  Version: Master
 All Classes Namespaces Files Functions Variables Typedefs Friends Pages
tgDataManager.cpp
Go to the documentation of this file.
1 /*
2  * Copyright © 2012, United States Government, as represented by the
3  * Administrator of the National Aeronautics and Space Administration.
4  * All rights reserved.
5  *
6  * The NASA Tensegrity Robotics Toolkit (NTRT) v1 platform is licensed
7  * under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  * http://www.apache.org/licenses/LICENSE-2.0.
11  *
12  * Unless required by applicable law or agreed to in writing,
13  * software distributed under the License is distributed on an
14  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
15  * either express or implied. See the License for the specific language
16  * governing permissions and limitations under the License.
17 */
18 
26 // This module
27 #include "tgDataManager.h"
28 // This application
29 #include "tgSensor.h"
30 #include "core/tgSenseable.h"
31 #include "tgSensorInfo.h"
32 // The C++ Standard Library
33 //#include <stdio.h> // for sprintf
34 #include <iostream>
35 #include <stdexcept>
36 #include <cassert>
37 
42 {
43  // Postcondition
44  assert(invariant());
45 }
46 
54 {
55  //DEBUGGING
56  //std::cout << "tgDataManager destructor." << std::endl;
57 
58  // First, delete everything in m_sensors.
59  const size_t n_Sens = m_sensors.size();
60  for (size_t i = 0; i < n_Sens; ++i)
61  {
62  // Pick out one sensor from the list:
63  tgSensor* const pSensor = m_sensors[i];
64  // TO-DO: check if we need this assert...
65  // It is safe to delete NULL, but this is an invariant
66  // assert(pChild != NULL);
67  delete pSensor;
68  // Null out the deleted pointer.
69  m_sensors[i] = NULL;
70  }
71  // Next, delete the sensor infos.
72  const size_t n_SensInf = m_sensorInfos.size();
73  for (size_t i = 0; i < n_SensInf; ++i)
74  {
75  // Pick out one sensorInfo from the list:
76  tgSensorInfo* const pSensorInfo = m_sensorInfos[i];
77  // TO-DO: check if we need this assert...
78  // assert(pChild != NULL);
79  delete pSensorInfo;
80  //Null out the deleted pointer.
81  m_sensorInfos[i] = NULL;
82  }
83 
84  // Note that the creation and deletion of the senseable objects, e.g.
85  // the tgModels, is handled externally.
86  // tgDataManagers should NOT destroy the objects they are sensing.
87 }
88 
93 void tgDataManager::addSensorsHelper(tgSenseable* pSenseable)
94 {
95  // Loop over all tgSensorInfos in the list.
96  for (size_t i=0; i < m_sensorInfos.size(); i++){
97  // If this particular sensor info is appropriate for the pSenseable,
98  if( m_sensorInfos[i]->isThisMySenseable(pSenseable) ) {
99  // Possibly create sensors (usually, this returns a list of size 1.
100  std::vector<tgSensor*> newSensors =
101  m_sensorInfos[i]->createSensorsIfAppropriate(pSenseable);
102  // Add everything in the list to m_sensors.
103  // If an empty list has been returned, no sensors will be added.
104  // Also, need to check if any of the pointers are NULL.
105  for( size_t i=0; i < newSensors.size(); i++ ){
106  // If this sensor pointer is not null...
107  if( newSensors[i] != NULL) {
108  m_sensors.push_back(newSensors[i]);
109  }
110  }
111  }
112  }
113 }
114 
122 {
123  // Iterate over all sensables and their descendants, adding sensors
124  // if appropriate.
125  for (size_t j=0; j < m_senseables.size(); j++){
126  // For each senseable object, create sensors for it and its descendants.
127  // First, the senseable itself:
128  addSensorsHelper(m_senseables[j]);
129  // Then, for all its descendants:
130  std::vector<tgSenseable*> descendants =
131  m_senseables[j]->getSenseableDescendants();
132  // Loop through.
133  for (size_t k=0; k < descendants.size(); k++) {
134  addSensorsHelper(descendants[k]);
135  }
136  }
137 
138  // Postcondition
139  assert(invariant());
140 }
141 
150 {
151  // First, delete the sensors.
152  // Note that it's good practice to set deleted pointers to NULL here.
153  for (std::size_t i = 0; i < m_sensors.size(); i++)
154  {
155  // Note that sensors don't have any teardown method.
156  // The delete method will call their destructors.
157  delete m_sensors[i];
158  m_sensors[i] = NULL;
159  }
160  // Clear the list so that the destructor for this class doesn't have to
161  // do anything.
162  m_sensors.clear();
163 
164  // Don't touch the list of senseable objects.
165  // These tgModels are not re-created when teardown is called (I think?),
166  // so the pointers should remain the same between calls to reset.
167  // TO-DO: confirm that it's OK to not remove the list of m_senseables.
168 
169  // Postcondition
170  assert(invariant());
171  assert(m_sensors.empty());
172 }
173 
178 void tgDataManager::step(double dt)
179 {
180  if (dt <= 0.0)
181  {
182  throw std::invalid_argument("dt is not positive");
183  }
184  else
185  {
186  // Nothing to do.
187  }
188 
189  // Postcondition
190  assert(invariant());
191 }
192 
199 {
200  // TO-DO:
201  // Check if a type of pSensorInfo is already in the list.
202  // Otherwise, duplicate sensors will be created: e.g., if two tgRodSensorInfos
203  // are in m_sensorInfos, then multiple tgRodSensors will be created for
204  // each tgRod.
205 
206  // Precondition
207  if (pSensorInfo == NULL)
208  {
209  throw std::invalid_argument("pSensorInfo is NULL inside tgDataManager::addSensorInfo");
210  }
211 
212  m_sensorInfos.push_back(pSensorInfo);
213 
214  // Postcondition
215  assert(invariant());
216  assert(!m_sensorInfos.empty());
217 }
218 
225 {
226  // Precondition
227  if (pSenseable == NULL)
228  {
229  throw std::invalid_argument("pSenseable is NULL inside tgDataManager::addSenseable");
230  }
231 
232  // TO-DO: should we check to see if this senseable object is already
233  // in the m_senseables list???
234  m_senseables.push_back(pSenseable);
235 
236  // Postcondition
237  assert(invariant());
238  assert(!m_senseables.empty());
239 }
240 
241 
246 std::string tgDataManager::toString() const
247 {
248  std::ostringstream os;
249  os << "tgDataManager"
250  << " with " << m_sensors.size() << " sensors, " << m_sensorInfos.size()
251  << " sensorInfos, and " << m_senseables.size() << " senseable objects."
252  << std::endl;
253 
254  return os.str();
255 }
256 
257 
258 bool tgDataManager::invariant() const
259 {
260  // TO-DO:
261  // m_sensors and m_sensorInfos are sane, check somehow...?
262  // For example, check if any of the pointers in m_sensors are NULL.
263  return true;
264 }
265 
266 std::ostream&
267 operator<<(std::ostream& os, const tgDataManager& obj)
268 {
269  os << obj.toString() << std::endl;
270  return os;
271 }
Constains definition of abstract class tgSensor, which defines the methods that a sensor must impleme...
std::vector< tgSensor * > m_sensors
virtual void addSenseable(tgSenseable *pSenseable)
virtual void teardown()
std::ostream & operator<<(std::ostream &os, const tgDataManager &obj)
virtual ~tgDataManager()
std::vector< tgSensorInfo * > m_sensorInfos
Contains the definition of class tgDataManager.
virtual void step(double dt)
virtual void addSensorInfo(tgSensorInfo *pSensorInfo)
std::vector< tgSenseable * > m_senseables
virtual void setup()
virtual std::string toString() const
Definition of abstract class tgSensorInfo.
Constains the implementation of mixin class tgSenseable.