NTRT Simulator  Version: Master
 All Classes Namespaces Files Functions Variables Typedefs Friends Pages
T6Model.cpp
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 
25 // This module
26 #include "T6Model.h"
27 // This library
28 #include "core/tgBasicActuator.h"
29 #include "core/tgRod.h"
30 #include "tgcreator/tgBuildSpec.h"
32 #include "tgcreator/tgRodInfo.h"
33 #include "tgcreator/tgStructure.h"
35 // The Bullet Physics library
36 #include "LinearMath/btVector3.h"
37 // The C++ Standard Library
38 #include <stdexcept>
39 
40 namespace
41 {
42  // Note: This current model of the SUPERball rod is 1.5m long by 4.5cm (0.045m) radius,
43  // which is 1.684m*pi*(0.040m)^2 = 0.008545132m^3.
44  // For SUPERball v1.5, mass = 3.5kg per strut, which density [kg/m^3] comes out to:
45  // density = 3.45kg/0.008545132m^3 = 403.738642402kg/m^3 = 0.403738642402 kg/dm^3
46 
47  // see tgBaseString.h for a descripton of some of these rod parameters
48  // (specifically, those related to the motor moving the strings.)
49  // NOTE that any parameter that depends on units of length will scale
50  // with the current gravity scaling. E.g., with gravity as 98.1
51  // Thus,
52  // Rod Length = 17.00
53  // Rod Radius = 0.40
54  // density = 0.40374 (length is cubed, so decimal moves 3 places)
55 
56  // similarly, frictional parameters are for the tgRod objects.
57  const struct Config
58  {
59  double density;
60  double radius;
61  double stiffness_passive;
62  double stiffness_active;
63  double damping;
64  double rod_length;
65  double rod_space;
66  double friction;
67  double rollFriction;
68  double restitution;
69  double pretension;
70  bool hist;
71  double maxTens;
72  double targetVelocity;
73  } c =
74  {
75  0.40374, // density (kg / length^3)
76  0.40, // radius (length)
77  998.25, // stiffness_passive (kg / sec^2)
78  3152.36, // stiffness_active (kg / sec^2)
79  50.0, // damping (kg / sec)
80  17.00, // rod_length (length)
81  17.00/4, // rod_space (length)
82  0.99, // friction (unitless)
83  0.01, // rollFriction (unitless)
84  0.0, // restitution (?)
85  399, // pretension
86  true, // History logging (boolean)
87  100000, // maxTens
88  10000, // targetVelocity
89 #if (0) // Removed 12/10/14
90  20000 // maxAcc
91 #endif
92  // Use the below values for earlier versions of simulation.
93  // 1.152, // density (kg / length^3)
94  // 0.45, // radius (length)
95  // 613.0, // stiffness_passive (kg / sec^2)
96  // 2854.5, // stiffness_active (kg / sec^2)
97  };
98 } // namespace
99 
101 {
102 }
103 
105 {
106 }
107 
108 void T6Model::addNodes(tgStructure& s)
109 {
110  const double half_length = c.rod_length / 2;
111 
112  s.addNode(-c.rod_space, -half_length, 0); // 0
113  s.addNode(-c.rod_space, half_length, 0); // 1
114  s.addNode( c.rod_space, -half_length, 0); // 2
115  s.addNode( c.rod_space, half_length, 0); // 3
116  s.addNode(0, -c.rod_space, -half_length); // 4
117  s.addNode(0, -c.rod_space, half_length); // 5
118  s.addNode(0, c.rod_space, -half_length); // 6
119  s.addNode(0, c.rod_space, half_length); // 7
120  s.addNode(-half_length, 0, c.rod_space); // 8
121  s.addNode( half_length, 0, c.rod_space); // 9
122  s.addNode(-half_length, 0, -c.rod_space); // 10
123  s.addNode( half_length, 0, -c.rod_space); // 11
124 }
125 
126 void T6Model::addRods(tgStructure& s)
127 {
128  s.addPair( 0, 1, "rod");
129  s.addPair( 2, 3, "rod");
130  s.addPair( 4, 5, "rod");
131  s.addPair( 6, 7, "rod");
132  s.addPair( 8, 9, "rod");
133  s.addPair(10, 11, "rod");
134 }
135 
136 void T6Model::addMuscles(tgStructure& s)
137 {
138  // Added ability to have two muscles in a structure.
139  // Configuration currently is random, at the moment [27 June 2014]
140  s.addPair(0, 4, "muscle_active");
141  s.addPair(0, 5, "muscle_passive");
142  s.addPair(0, 8, "muscle_active");
143  s.addPair(0, 10, "muscle_passive");
144 
145  s.addPair(1, 6, "muscle_active");
146  s.addPair(1, 7, "muscle_passive");
147  s.addPair(1, 8, "muscle_passive");
148  s.addPair(1, 10, "muscle_active");
149 
150  s.addPair(2, 4, "muscle_passive");
151  s.addPair(2, 5, "muscle_active");
152  s.addPair(2, 9, "muscle_active");
153  s.addPair(2, 11, "muscle_passive");
154 
155  s.addPair(3, 7, "muscle_active");
156  s.addPair(3, 6, "muscle_passive");
157  s.addPair(3, 9, "muscle_passive");
158  s.addPair(3, 11, "muscle_active");
159 
160  s.addPair(4, 10, "muscle_active");
161  s.addPair(4, 11, "muscle_passive");
162 
163  s.addPair(5, 8, "muscle_active");
164  s.addPair(5, 9, "muscle_passive");
165 
166  s.addPair(6, 10, "muscle_passive");
167  s.addPair(6, 11, "muscle_active");
168 
169  s.addPair(7, 8, "muscle_passive");
170  s.addPair(7, 9, "muscle_active");
171 
172 }
173 
175 {
176 
177  const tgRod::Config rodConfig(c.radius, c.density, c.friction,
178  c.rollFriction, c.restitution);
179 
181  tgBasicActuator::Config muscleConfig_passive(c.stiffness_passive, c.damping, c.pretension, c.hist,
182  c.maxTens, c.targetVelocity);
183 
184  tgBasicActuator::Config muscleConfig_active(c.stiffness_active, c.damping, c.pretension, c.hist,
185  c.maxTens, c.targetVelocity);
186 
187  // Start creating the structure
188  tgStructure s;
189  addNodes(s);
190  addRods(s);
191  addMuscles(s);
192  s.move(btVector3(0, 10, 0));
193 
194  // Add a rotation. This is needed if the ground slopes too much,
195  // otherwise glitches put a rod below the ground.
196  btVector3 rotationPoint = btVector3(0, 0, 0); // origin
197  btVector3 rotationAxis = btVector3(0, 1, 0); // y-axis
198  double rotationAngle = M_PI/2;
199  s.addRotation(rotationPoint, rotationAxis, rotationAngle);
200 
201  // Create the build spec that uses tags to turn the structure into a real model
202  tgBuildSpec spec;
203  spec.addBuilder("rod", new tgRodInfo(rodConfig));
204  spec.addBuilder("muscle_passive", new tgBasicActuatorInfo(muscleConfig_passive));
205  spec.addBuilder("muscle_active", new tgBasicActuatorInfo(muscleConfig_active));
206 
207  // Create your structureInfo
208  tgStructureInfo structureInfo(s, spec);
209 
210  // Use the structureInfo to build ourselves
211  structureInfo.buildInto(*this, world);
212 
213  // We could now use tgCast::filter or similar to pull out the
214  // models (e.g. muscles) that we want to control.
215  allMuscles = tgCast::filter<tgModel, tgBasicActuator> (getDescendants());
216  // Not really sure how to use the find() function in tgModel.h
217  passiveMuscles = tgCast::find<tgModel, tgBasicActuator>(tgTagSearch("muscle_passive"), getDescendants());
218  activeMuscles = tgCast::find<tgModel, tgBasicActuator>(tgTagSearch("muscle_active"), getDescendants());
219 
220  // call the onSetup methods of all observed things e.g. controllers
221  notifySetup();
222 
223  // Actually setup the children
224  tgModel::setup(world);
225 }
226 
227 void T6Model::step(double dt)
228 {
229  // Precondition
230  if (dt <= 0.0)
231  {
232  throw std::invalid_argument("dt is not positive");
233  }
234  else
235  {
236  // Notify observers (controllers) of the step so that they can take action
237  notifyStep(dt);
238  tgModel::step(dt); // Step any children
239  }
240 }
241 
243 {
244  tgModel::onVisit(r);
245 }
246 
247 const std::vector<tgBasicActuator*>& T6Model::getAllMuscles() const
248 {
249  return allMuscles;
250 }
251 
252 const std::vector<tgBasicActuator*>& T6Model::getPassiveMuscles() const
253 {
254  return passiveMuscles;
255 }
256 
257 const std::vector<tgBasicActuator*>& T6Model::getActiveMuscles() const
258 {
259  return activeMuscles;
260 }
261 
262 const double T6Model::muscleRatio()
263 {
264  return (c.stiffness_passive/c.stiffness_active);
265  //return 2.5;
266 }
267 
269 {
271 }
virtual void teardown()
Definition: tgModel.cpp:68
virtual void setup(tgWorld &world)
Definition: tgModel.cpp:57
Definition of class tgRodInfo.
virtual void step(double dt)
Definition: tgModel.cpp:84
virtual void onVisit(tgModelVisitor &r)
Definition: T6Model.cpp:242
const std::vector< tgBasicActuator * > & getAllMuscles() const
Definition: T6Model.cpp:247
const std::vector< tgBasicActuator * > & getPassiveMuscles() const
Definition: T6Model.cpp:252
Definition of class tgBasicActuatorInfo.
virtual void onVisit(const tgModelVisitor &r) const
Definition: tgModel.cpp:107
virtual void setup(tgWorld &world)
Definition: T6Model.cpp:174
void addPair(int fromNodeIdx, int toNodeIdx, std::string tags="")
Definition: tgStructure.cpp:80
void addRotation(const btVector3 &fixedPoint, const btVector3 &axis, double angle)
void teardown()
Definition: T6Model.cpp:268
Contains the definition of class tgBasicActuator.
virtual void step(double dt)
Definition: T6Model.cpp:227
virtual ~T6Model()
Definition: T6Model.cpp:104
Definition of class tgStructure.
Definition of class tgStructureInfo.
const std::vector< tgBasicActuator * > & getActiveMuscles() const
Definition: T6Model.cpp:257
T6Model()
Definition: T6Model.cpp:100
virtual const double muscleRatio()
Definition: T6Model.cpp:262
Contains the definition of class tgRod.
Definition of class tgBuildSpec.
void notifyStep(double dt)
std::vector< tgModel * > getDescendants() const
Definition: tgModel.cpp:170
void buildInto(tgModel &model, tgWorld &world)
void addNode(double x, double y, double z, std::string tags="")
Definition: tgStructure.cpp:70