NTRT Simulator  Version: Master
 All Classes Namespaces Files Functions Variables Typedefs Friends Pages
tgCPGMGActuatorControl.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 
28 #include "tgCPGMGActuatorControl.h"
29 
30 #include "core/tgSpringCable.h"
33 #include "core/tgBasicActuator.h"
36 #include "util/CPGEquations.h"
37 #include "core/tgCast.h"
38 
39 // The C++ Standard Library
40 #include <iostream>
41 #include <stdexcept>
42 #include <vector>
43 
44 tgCPGMGActuatorControl::tgCPGMGActuatorControl(const double controlStep) :
45 m_controlTime(0.0),
46 m_totalTime(0.0),
47 m_controlStep(controlStep),
48 m_commandedTension(0.0),
49 m_pFromBody(NULL),
50 m_pToBody(NULL)
51 {
52  if (m_controlStep < 0.0)
53  {
54  throw std::invalid_argument("Negative control step");
55  }
56 }
57 
58 tgCPGMGActuatorControl::~tgCPGMGActuatorControl()
59 {
60  // We don't own these
61  m_pFromBody = NULL;
62  m_pToBody = NULL;
63 }
64 
66 {
67  m_controlLength = subject.getStartLength();
68 
69  // tgSpringCable doesn't know about bullet anchors, so we have to cast here to get the rigid bodies
70  std::vector<const tgBulletSpringCableAnchor*> anchors =
71  tgCast::filter<const tgSpringCableAnchor, const tgBulletSpringCableAnchor>(subject.getSpringCable()->getAnchors());
72 
73  std::size_t n = anchors.size();
74  assert(n >= 2);
75 
76  m_pFromBody = anchors[0]->attachedBody;
77  m_pToBody = anchors[n - 1]->attachedBody;
78 }
79 
81 {
82  m_controlTime += dt;
83  m_totalTime += dt;
86 
87  // Workaround until we implement PID
88  tgBasicActuator& m_sca = *(tgCast::cast<tgSpringCableActuator, tgBasicActuator>(subject));
89 
91  {
92 
93  m_commandedTension = motorControl().control(m_sca, m_controlTime, controlLength(), getCPGValue());
94 
95  m_controlTime = 0;
96  }
97  else
98  {
99  m_sca.moveMotors(dt);
100  }
101 }
102 
103 void tgCPGMGActuatorControl::assignNodeNumber (CPGEquations& CPGSys, array_2D nodeParams)
104 {
105  // Ensure that this hasn't already been assigned
106  assert(m_nodeNumber == -1);
107 
108  m_pCPGSystem = &CPGSys;
109 
110  std::vector<double> params (7);
111  params[0] = nodeParams[0][0]; // Frequency Offset
112  params[1] = nodeParams[0][0]; // Frequency Scale
113  params[2] = nodeParams[0][1]; // Radius Offset
114  params[3] = nodeParams[0][1]; // Radius Scale
115  params[4] = 20.0; // rConst (a constant)
116  params[5] = 0.0; // dMin for descending commands
117  params[6] = 5.0; // dMax for descending commands
118 
119  m_nodeNumber = m_pCPGSystem->addNode(params);
120 }
121 
122 void
123 tgCPGMGActuatorControl::setConnectivity(const std::vector<tgCPGMGActuatorControl*>& allStrings,
124  array_3D edgeParams)
125 {
126  assert(m_nodeNumber >= 0);
127 
128  //int muscleSize = edgeParams.shape()[1];
129 
130  std::vector<int> connectivityList;
131  std::vector<double> weights;
132  std::vector<double> phases;
133 
134  // Assuming all coupling is two way, there ought to be a way
135  // to search faster than O((2N)^2) since every other
136  // string has to call this. Ideas are welcome
137  for (int i = 0; i < allStrings.size(); i++)
138  {
139  if (this != allStrings[i])
140  {
141  // Make sure we're dealing with the same system
142  assert(m_pCPGSystem == allStrings[i]->getCPGSys());
143 
144  const btRigidBody* theirFromGroup = allStrings[i]->getFromBody();
145  const btRigidBody* theirToGroup = allStrings[i]->getToBody();
146 
147  // "All to all" connectivity for shared rigid bodies
148  if(m_pFromBody == theirFromGroup ||
149  m_pToBody == theirToGroup ||
150  m_pFromBody == theirToGroup ||
151  m_pToBody == theirFromGroup)
152  {
153  int theirMuscle = allStrings[i]->getNodeNumber();
154  // Integer division: -1 is behind, 0 is same row 1 is ahead
155  //int rp = ((m_nodeNumber - theirMuscle) / muscleSize) + 1;
156  int j = m_nodeNumber;
157  int k = theirMuscle;
158  connectivityList.push_back(theirMuscle);
159  // Upper triangular matrix, lower number always goes first
160  if(j > k){
161  weights.push_back(edgeParams[k][j][0]);
162  phases.push_back(edgeParams[k][j][1]);
163  }
164  else
165  {
166  weights.push_back(edgeParams[j][k][0]);
167  phases.push_back(edgeParams[j][k][1]);
168  }
169  }
170  }
171  }
172 
173  m_pCPGSystem->defineConnections(m_nodeNumber, connectivityList, weights, phases);
174 }
175 
176 void tgCPGMGActuatorControl::setupControl(tgImpedanceController& ipc)
177 {
178  tgBaseCPGNode::setupControl(ipc);
179 }
180 
181 void tgCPGMGActuatorControl::setupControl(tgImpedanceController& ipc,
182  double controlLength)
183 {
184  if (controlLength < 0.0)
185  {
186  throw std::invalid_argument("Negative control length");
187  }
188 
189  m_controlLength = controlLength;
190  tgBaseCPGNode::setupControl(ipc);
191 }
192 
Contains the definition of class ImpedanceControl. $Id$.
Definition of the tgCPGStringControl observer class.
Definitions of class tgSpringCable.
virtual void moveMotors(double dt)
void assignNodeNumber(CPGEquations &CPGSys, array_2D nodeParams)
virtual const double getStartLength() const
void setConnectivity(const std::vector< tgCPGMGActuatorControl * > &allStrings, array_3D edgeParams)
Utility class for class casting and filtering collections by type.
virtual void onStep(tgSpringCableActuator &subject, double dt)
Contains the definition of abstract base class tgSpringCableActuator. Assumes that the string is line...
const CPGEquations * getCPGSys() const
Contains the definition of class tgBasicActuator.
virtual void onAttach(tgSpringCableActuator &subject)
virtual const std::vector< const tgSpringCableAnchor * > getAnchors() const =0
Definitions of class tgBulletSpringCableAnchor, formerly muscleAnchor.
Definition of class CPGEquations.
Definitions of class tgSpringCableAnchor.
double control(tgBasicController &mLocalController, double deltaTimeSeconds, double newPosition, double offsetVel=0)
Control Functions.
const tgSpringCable * getSpringCable() const