71 const std::lock_guard<std::recursive_mutex> lock(
mtx_mps);
75 std::map<std::string, bool> flagMPToStop;
76 for (
auto& pair :
limb)
78 flagMPToStop[pair.first] = not
limb.at(pair.first)->controller.ftsensor.ftSafe.load();
79 pair.second->nonRTDeltaT =
80 pair.second->rtStatusInNonRT.accumulateTime - pair.second->nonRTAccumulateTime;
81 pair.second->nonRTAccumulateTime = pair.second->rtStatusInNonRT.accumulateTime;
85 for (
auto& pair :
hands->hands)
87 pair.second->nonRTDeltaT =
88 pair.second->rtsInNonRT.accumulateTime - pair.second->nonRTAccumulateTime;
89 pair.second->nonRTAccumulateTime = pair.second->rtsInNonRT.accumulateTime;
93 std::map<std::string, bool> mpRunning;
96 const auto mpNodeSet =
mp.second.mp->getNodeSetName();
97 mpRunning[
mp.second.mp->getMPName()] =
mp.second.mp->isRunning();
100 auto search = flagMPToStop.find(mpNodeSet);
101 if (search != flagMPToStop.end() and flagMPToStop.at(mpNodeSet) and
102 mp.second.mp->isRunning() and
103 (
limb.at(mpNodeSet)->controller.ftsensor.isForceGuardEnabled() or
104 limb.at(mpNodeSet)->controller.ftsensor.isTorqueGuardEnabled()))
106 mp.second.mp->stop();
107 ARMARX_INFO <<
"Due to force/torque safe guard, MP " <<
mp.second.mp->getMPName()
108 <<
" is stopped at " <<
mp.second.mp->getCanonicalValue();
111 if (
mp.second.mp->isFinished())
115 if (
mp.second.mp->getRole() ==
"taskspace")
117 auto& arm =
limb.at(
mp.second.mp->getNodeSetName());
118 if (
mp.second.mp->isFirstRun())
123 const std::vector<double> mpStart =
mp.second.mp->getStartVec();
125 if (
mp.second.mp->getStartFromPrevTarget() or
127 arm->rtStatusInNonRT.currentPose,
130 "TSMP initial start pose",
131 arm->nonRtConfig.safeDistanceMMToGoal,
132 arm->nonRtConfig.safeRotAngleDegreeToGoal,
133 mp.second.mp->getMPName() +
"mp_set_target"))
135 if (
mp.second.mp->getStartFromPrevTarget())
137 ARMARX_INFO <<
"User requested to start the current TS MP from the "
138 "previous target pose";
143 <<
"deviation from current pose too large, reset MP start pose";
145 mp.second.mp->validateInitialState(
151 in->pose = arm->rtStatusInNonRT.currentPose;
152 in->vel = arm->rtStatusInNonRT.currentTwist;
154 in->deltaT = arm->nonRTDeltaT;
156 else if (
mp.second.mp->getRole() ==
"nullspace")
158 auto& arm =
limb.at(
mp.second.mp->getNodeSetName());
161 arm->rtStatusInNonRT.jointPosition.size());
162 in->angleRadian = arm->rtStatusInNonRT.jointPosition;
163 in->angularVel = arm->rtStatusInNonRT.qvelFiltered;
164 in->deltaT = arm->nonRTDeltaT;
166 else if (
mp.second.mp->getRole() ==
"hand")
168 auto&
hand =
hands->hands.at(
mp.second.mp->getNodeSetName());
171 in->deltaT =
hand->nonRTDeltaT;
174 if (not rtTargetSafe)
184 runMPs(rtTargetSafe and ftSafe);
189 if (not mpRunning.at(
mp.second.mp->getMPName()))
193 for (
auto& ftGuard :
mpConfig.ftGuard)
195 if (ftGuard.mpName ==
mp.second.mp->getMPName())
197 bool const forceGuard =
198 (ftGuard.force.has_value() and
199 ftGuard.force.value() >=
mp.second.mp->getCanonicalValue());
200 bool const torqueGuard =
201 (ftGuard.torque.has_value() and
202 ftGuard.torque.value() >=
mp.second.mp->getCanonicalValue());
204 auto& arm =
limb.at(
mp.second.mp->getNodeSetName());
205 bool const resetForce =
206 not arm->controller.ftsensor.isForceGuardEnabled() and forceGuard;
207 bool const resetTorque =
208 not arm->controller.ftsensor.isTorqueGuardEnabled() and torqueGuard;
209 if (resetForce or resetTorque)
211 ARMARX_INFO <<
"Triggering force torque safety guard for "
212 << arm->kinematicChainName <<
" at can value "
213 <<
mp.second.mp->getCanonicalValue();
216 arm->nonRtConfig.ftConfig.enableSafeGuardForce = forceGuard;
217 arm->nonRtConfig.ftConfig.enableSafeGuardTorque = torqueGuard;
218 arm->controller.ftsensor.enableSafeGuard(resetForce, resetTorque);
222 if (
mp.second.mp->getRole() ==
"taskspace")
224 auto& arm =
limb.at(
mp.second.mp->getNodeSetName());
230 arm->rtStatusInNonRT.currentPose,
234 arm->nonRtConfig.safeDistanceMMToGoal,
235 arm->nonRtConfig.safeRotAngleDegreeToGoal,
236 mp.second.mp->getMPName() +
"mp_set_target");
237 arm->nonRtConfig.desiredPose = out->pose;
238 arm->nonRtConfig.desiredTwist = out->vel;
240 else if (
mp.second.mp->getRole() ==
"nullspace")
242 auto& arm =
limb.at(
mp.second.mp->getNodeSetName());
245 arm->nonRtConfig.desiredNullspaceJointAngles.value() = out->angleRadian;
247 else if (
mp.second.mp->getRole() ==
"hand")
250 auto&
hand =
hands->hands.at(
mp.second.mp->getNodeSetName());
253 out->angleRadian.size());
254 hand->targetNonRT.jointPosition.value() = out->angleRadian;
256 if (mpRunning.at(
mp.second.mp->getMPName()) and
mp.second.mp->isFinished())
258 ARMARX_INFO <<
"reset buffer for nonRtConfig of " <<
mp.second.mp->getMPName();
259 for (
auto& pair :
limb)
261 auto& arm = pair.second;
262 arm->bufferConfigUserToNonRt.reinitAllBuffers(arm->nonRtConfig);
264 for (
auto& pair :
limb)
266 userConfig.limbs.at(pair.first) = pair.second->nonRtConfig;