MPPool.cpp
Go to the documentation of this file.
1#include "MPPool.h"
2
3#include <SimoxUtility/json.h>
4#include <VirtualRobot/Nodes/RobotNode.h>
5
8
12#include <armarx/control/common/mp/aron/MPConfig.aron.generated.h>
13
14#include "../utils.h"
15#include "JSMP.h"
16#include "KeypointsMP.h"
17#include "TSMP.h"
18
20{
21
22 void
23 MPPool::createMPs(const MPListConfig& mpListConfig)
24 {
25 auto start = IceUtil::Time::now().toSecondsDouble();
26 ARMARX_INFO << "----------------------------------- creating MPs "
27 "-------------------------------------------------";
28 ARMARX_VERBOSE << " -- in MPPool, we have " << mpListConfig.mpList.size() << " MPs";
29 phaseStops_.clear();
30
31 int index = 0;
32 for (const MPConfig& c : mpListConfig.mpList)
33 {
34 auto className = mpClass::_from_string_nocase(c.className.c_str());
35 ARMARX_INFO << "-- (" << index << ") creating MP with name " << c.name
36 << "\n---- class: " << c.className << "\n---- type: " << c.mpTypeString
37 << "\n---- mode: " << c.mpMode << "\n---- style: " << c.mpStyle
38 << "\n---- group: " << c.group.toString()
39 << (c.enablePhaseStop ? "\n---- phase stop active " : "");
40 index++;
41 phaseStops_.try_emplace(c.group, PhaseStopResult{});
42 switch (className)
43 {
44 case mpClass::JSMP:
45 {
46 JSMPPtr jsmp(new JSMP(c));
47 JSMPInputPtr in(new JSMPInput());
48 JSMPOutputPtr out(new JSMPOutput());
49 mps.insert({c.name, {jsmp, in, out}});
50 break;
51 }
52 case mpClass::JSVelMP:
53 break;
54 case mpClass::TSMP:
55 {
56 TSMPPtr tsmp(new TSMP(c));
57 TSMPInputPtr in(new TSMPInput());
58 TSMPOutputPtr out(new TSMPOutput());
59 mps.insert({c.name, {tsmp, in, out}});
60
61 break;
62 }
63 case mpClass::KeypointsMP:
64 {
65 KeypointsMPPtr tsmp(new KeypointsMP(c));
68 mps.insert({c.name, {tsmp, in, out}});
69 break;
70 }
71 case mpClass::TSVelMP:
72 break;
73 default:
74 ARMARX_WARNING << "unsupported MP class: " << c.className
75 << "\nsupported names include: "
76 "JSMP, JSVelMP, TSMP, TSVelMP, KeypointsMP";
77 break;
78 }
79 }
80 auto duration = IceUtil::Time::now().toSecondsDouble() - start;
81 std::string allGroups;
82 for (auto& pair : phaseStops_)
83 {
84 if (not allGroups.empty())
85 {
86 allGroups += ", ";
87 }
88 allGroups += pair.first.toString();
89 }
90 ARMARX_VERBOSE << "-- created phase stop variables for groups: " << allGroups;
91 ARMARX_VERBOSE << "---------------------------------- All MPs created in " << duration
92 << " sec "
93 "-----------------------------------------------";
94 }
95
96 void
97 MPPool::reconfigureMPs(const MPListConfig& mpListConfig)
98 {
99 mps.clear();
100 createMPs(mpListConfig);
101 }
102
103 void
104 MPPool::runMPs(const bool rtSafe)
105 {
106 // std::map<std::string, PhaseStopResult> phaseStops;
107 /// Since there may be MPs for TCP, posture and fingers, we group those for one arm to use
108 /// the same phase stop signal, usually it is a good choice to use the Task Space MP to
109 /// compute the phase stop signal and propagate this to other mps in the same group
110 /// Compute phase stop
111 for (auto& mp : mps)
112 {
113 if ((rtSafe or mp.second.mp->isFirstRun()) and mp.second.mp->isTaskSpaceMP())
114 {
115 auto& phaseStop = phaseStops_.at(mp.second.mp->getGroup());
116 mp.second.mp->computePhaseStop(mp.second.input, mp.second.output, phaseStop);
117 }
118 }
119
120 /// propagate phase top to other mps
121 for (auto& mp : mps)
122 {
123 if (rtSafe or mp.second.mp->isFirstRun())
124 {
125 auto& phaseStop = phaseStops_.at(mp.second.mp->getGroup());
126 mp.second.mp->run(mp.second.input, mp.second.output, phaseStop);
127 }
128 }
129 }
130
131 std::string
132 MPPool::getNames(const Ice::Current& /*iceCurrent*/)
133 {
134 std::string allMPs = "";
135 for (const auto& mp : mps)
136 {
137 if (!allMPs.empty())
138 {
139 allMPs += ", ";
140 }
141 allMPs += mp.second.mp->getMPName();
142 }
143 return allMPs;
144 }
145
146 void
147 MPPool::set(const ::armarx::StringDoubleSeqMap& startVec,
148 const ::armarx::StringDoubleSeqMap& goalVec,
149 const ::armarx::StringDoubleMap& durationSec,
150 const ::Ice::Current& /*unused*/)
151 {
152 for (auto& pair : mps)
153 {
154 auto it = durationSec.find(pair.first);
155 auto is = startVec.find(pair.first);
156 auto ig = goalVec.find(pair.first);
157
158 if (it != durationSec.end())
159 {
160 if (it->second > 0.0)
161 {
162 pair.second.mp->setDurationSec(it->second);
163 }
164 }
165 if (is != startVec.end())
166 {
167 pair.second.mp->setStart(is->second);
168 }
169 if (ig != goalVec.end())
170 {
171 pair.second.mp->setGoal(ig->second);
172 }
173 }
174 }
175
176 void
177 MPPool::startAll(const Ice::Current& /*iceCurrent*/)
178 {
179 start();
180 }
181
182 void
183 MPPool::start(const std::string& mpName,
184 const DVec& startVec,
185 const DVec& goalVec,
186 Ice::Double timeDuration,
187 const Ice::Current& /*iceCurrent*/)
188 {
189 auto start = IceUtil::Time::now().toSecondsDouble();
190 if (mpName == "all")
191 {
192 ARMARX_VERBOSE << "--------------------------------------- start all MPs "
193 "---------------------------------------";
194 ARMARX_VERBOSE << " -- To start all MPs at once, it's up to the user to configure the "
195 "start, goal and timeduration properly before this call.";
196 int index = 0;
197 for (auto& mp : mps)
198 {
199 ARMARX_VERBOSE << " -- (" << index << ")-th MP: ";
200 mp.second.mp->start();
201 index++;
202 }
203 ARMARX_VERBOSE << " -- all MPs started.";
204 }
205 else
206 {
207 auto search = mps.find(mpName);
208 if (search != mps.end())
209 {
210 if (timeDuration < 0.0)
211 {
212 search->second.mp->start(goalVec, startVec);
213 }
214 else
215 {
216 search->second.mp->start(goalVec, startVec, timeDuration);
217 }
218 }
219 else
220 {
221 ARMARX_ERROR << mpName
222 << " is not in the MP pool. Please check your configuration file";
223 }
224 }
225 // ARMARX_IMPORTANT << "starting mp" << VAROUT(mpName) << "with start: " << dVecToString(startVec) << " and goal: " << dVecToString(goalVec) << " for " << timeDuration << " seconds";
226 auto duration = IceUtil::Time::now().toSecondsDouble() - start;
227 ARMARX_INFO << "All mp started in " << duration << " sec.";
228 }
229
230 void
231 MPPool::stopAll(const Ice::Current& /*iceCurrent*/)
232 {
233 stop();
234 }
235
236 void
237 MPPool::requestStop(const std::string& mpName, const Ice::Current& /*unused*/)
238 {
239 if (mpName == "all")
240 {
241 for (auto& mp : mps)
242 {
243 mp.second.mp->requestStop();
244 }
245 }
246 else
247 {
248 auto search = mps.find(mpName);
249 if (search != mps.end())
250 {
251 search->second.mp->requestStop();
252 }
253 else
254 {
255 ARMARX_ERROR << mpName
256 << " is not in the MP pool. Please check your configuration file";
257 }
258 }
259 }
260
261 void
262 MPPool::stop(const std::string& mpName, const Ice::Current& /*unused*/)
263 {
264 if (mpName == "all")
265 {
266 for (auto& mp : mps)
267 {
268 mp.second.mp->stop();
269 }
270 }
271 else
272 {
273 auto search = mps.find(mpName);
274 if (search != mps.end())
275 {
276 search->second.mp->stop();
277 }
278 else
279 {
280 ARMARX_ERROR << mpName
281 << " is not in the MP pool. Please check your configuration file";
282 }
283 }
284 }
285
286 void
287 MPPool::pauseAll(const Ice::Current& /*iceCurrent*/)
288 {
289 pause();
290 }
291
292 void
293 MPPool::pause(const std::string& mpName, const Ice::Current& /*unused*/)
294 {
295 if (mpName == "all")
296 {
297 for (auto& mp : mps)
298 {
299 mp.second.mp->pause();
300 }
301 }
302 else
303 {
304 auto search = mps.find(mpName);
305 if (search != mps.end())
306 {
307 search->second.mp->pause();
308 }
309 else
310 {
311 ARMARX_ERROR << mpName
312 << " is not in the MP pool. Please check your configuration file";
313 }
314 }
315 }
316
317 void
318 MPPool::resumeAll(const Ice::Current& /*iceCurrent*/)
319 {
320 resume();
321 }
322
323 void
324 MPPool::resume(const std::string& mpName, const Ice::Current& /*unused*/)
325 {
326 if (mpName == "all")
327 {
328 for (auto& mp : mps)
329 {
330 mp.second.mp->resume();
331 }
332 }
333 else
334 {
335 auto search = mps.find(mpName);
336 if (search != mps.end())
337 {
338 search->second.mp->resume();
339 }
340 else
341 {
342 ARMARX_ERROR << mpName
343 << " is not in the MP pool. Please check your configuration file";
344 }
345 }
346 }
347
348 void
349 MPPool::resetAll(const Ice::Current& /*iceCurrent*/)
350 {
351 reset();
352 }
353
354 void
355 MPPool::reset(const std::string& mpName, const Ice::Current& /*unused*/)
356 {
357 if (mpName == "all")
358 {
359 for (auto& mp : mps)
360 {
361 mp.second.mp->reset();
362 }
363 }
364 else
365 {
366 auto search = mps.find(mpName);
367 if (search != mps.end())
368 {
369 search->second.mp->reset();
370 }
371 else
372 {
373 ARMARX_ERROR << mpName
374 << " is not in the MP pool. Please check your configuration file";
375 }
376 }
377 }
378
379 bool
380 MPPool::isFinishedAll(const Ice::Current& /*iceCurrent*/)
381 {
382 return isFinished();
383 }
384
385 bool
386 MPPool::isFinished(const std::string& mpName, const Ice::Current& /*unused*/)
387 {
388 if (mpName == "all")
389 {
390 return std::all_of(mps.begin(),
391 mps.end(),
392 [](const auto& pair) { return pair.second.mp->isFinished(); });
393 }
394
395 auto it = mps.find(mpName);
396 if (it != mps.end())
397 {
398 return it->second.mp->isFinished();
399 }
400
401 ARMARX_ERROR << mpName << " is not in the MP pool. Please check your configuration file";
402 return true;
403 }
404
405 void
406 MPPool::learnFromCSV(const Ice::StringSeq& fileNames, const Ice::Current& /*iceCurrent*/)
407 {
408 if (!fileNames.empty())
409 {
410 ARMARX_WARNING << "Be aware that the fileNames ice parameter is not yet used. "
411 << "Instead, set the file names in the MPConfig parameter of your "
412 << "previous ice interface call.";
413 }
414 ARMARX_INFO << "--------------------------------------- Train MPs "
415 "----------------------------------------------------";
416 for (auto& mp : mps)
417 {
418 mp.second.mp->learnFromCSV();
419 }
420 isMPReady.store(true);
421 ARMARX_VERBOSE << "--------------------------------------- done "
422 "----------------------------------------------------";
423 }
424
425 void
426 MPPool::learnFromTrajs(const ::armarx::aron::data::dto::DictPtr& dict,
427 const Ice::Current& /*iceCurrent*/)
428 {
429 auto start = IceUtil::Time::now().toSecondsDouble();
430 ARMARX_INFO << "--------------------------------------- Train MPs "
431 "----------------------------------------------------";
432
433 // Convert parameter of ice interface call to business object
434 MultiMPTrajs trajsDict;
435 trajsDict.fromAron(dict);
436 // std::map<std::string, std::vector<arondto::MPTraj>> dto =
437 // arondto::MultiMPTrajs::FromAron(dict).data;
438 // // armarx::aron::fromAron<std::vector<arondto::MPTraj>, MPTrajs>(arondto::MultiMPTrajs::FromAron(dict), bo);
439 // armarx::aron::fromAron<std::string, std::vector<arondto::MPTraj>, std::string, MPTrajs>(
440 // dto, trajsDict);
441
442 // MultiMPTrajs trajsDict = ::armarx::fromAronDict<arondto::MultiMPTrajs, MultiMPTrajs>(dict);
443
444 if (trajsDict.data.empty())
445 {
446 ARMARX_INFO << "Learning from trajectories specified in MPConfig(s) rather than as an "
447 "ice parameter";
448 for (const auto& [mpName, mpInputOutput] : mps)
449 {
450 const auto& mpConfig = mpInputOutput.mp->getConfig();
451 ARMARX_CHECK(not mpConfig.trajectoryList.empty())
452 << "For MP " << mpName << ": No trajectories provided as parameter, "
453 << "and not trajectories specified in MPConfig.";
454 mpInputOutput.mp->learnFromTraj(mpConfig.trajectoryList);
455 }
456 }
457 else
458 {
459 for (const auto& [mpName, trajs] : trajsDict.data)
460 {
461 // Learn the MP identified by mpName from the trajectory list stored in
462 // trajsDict.at(mpName)
463 ARMARX_CHECK(mps.count(mpName))
464 << "Trajectories provided for unknown MP " << mpName;
465 ARMARX_CHECK(not trajs.empty())
466 << "Empty list of trajectories provided for MP " << mpName;
467 mps.at(mpName).mp->learnFromTraj(trajs);
468 }
469 }
470 // mark whole MP pool as ready
471 isMPReady.store(true);
472
473 auto duration = IceUtil::Time::now().toSecondsDouble() - start;
474 ARMARX_VERBOSE << "--------------------------------------- done in " << duration
475 << " sec "
476 "----------------------------------------------------";
477 }
478
479 void
480 MPPool::trainMP(const Ice::Current& /*iceCurrent*/)
481 {
482 auto start = IceUtil::Time::now().toSecondsDouble();
483 for (auto& mp : mps)
484 {
485 mp.second.mp->trainMP();
486 }
487 isMPReady.store(true);
488 auto duration = IceUtil::Time::now().toSecondsDouble() - start;
489 ARMARX_VERBOSE << "training finished in " << duration << " sec.";
490 }
491
492 void
493 MPPool::setGoal(const DVec& /*goals*/, const Ice::Current& /*iceCurrent*/)
494 {
495 }
496
497 void
499 const DVec& goals,
500 const Ice::Current& /*iceCurrent*/)
501 {
502 for (auto& mp : mps)
503 {
504 mp.second.mp->setStartAndGoal(starts, goals);
505 }
506 }
507
508 void
509 MPPool::setViaPoint(Ice::Double /*u*/,
510 const DVec& /*viapoint*/,
511 const Ice::Current& /*iceCurrent*/)
512 {
513 }
514
515 void
516 MPPool::removeAllViaPoint(const Ice::Current& /*iceCurrent*/)
517 {
518 }
519
520 //void MPPool::setWeight(const DVecSeq& weights, const Ice::Current &iceCurrent)
521 //{
522
523 //}
524
525 std::string
526 MPPool::serialize(const Ice::Current& /*iceCurrent*/)
527 {
528 return "";
529 }
530
531 DVec
532 MPPool::deserialize(const std::string& /*unused*/, const Ice::Current& /*iceCurrent*/)
533 {
534 std::vector<double> test{0.1, 0.1};
535 return test;
536 }
537
538 Ice::Double
539 MPPool::getCanVal(const std::string& mpName, const Ice::Current& /*iceCurrent*/)
540 {
541 auto search = mps.find(mpName);
542 if (search != mps.end())
543 {
544 return search->second.mp->getCanonicalValue();
545 }
546 ARMARX_ERROR << mpName << " is not in the MP pool. Please check your configuration file";
547 return 1.0;
548 }
549
550 bool
551 MPPool::getMPEnabled(const Ice::Current& /*unused*/)
552 {
553 return true;
554 }
555
556 void
557 MPPool::updateMPConfig(const ::armarx::aron::data::dto::DictPtr& /*dto*/,
558 const Ice::Current& /*iceCurrent*/)
559 {
560 ARMARX_WARNING << "You should overwrite this method in your concrete MP controllers, and "
561 "call resetMPs(dto, rnsMap)";
562 }
563
564 bool
565 MPPool::resetMPs(const ::armarx::aron::data::dto::DictPtr& dto,
566 const std::map<std::string, VirtualRobot::RobotNodeSetPtr>& rnsMap)
567 {
568 std::scoped_lock lock(mtx_mps);
569 if (not isFinishedAll())
570 {
571 ARMARX_WARNING << "MP is not finished yet, cannot reset MP\n"
572 "If you want to force reset, please call \n\n"
573 " ctrl->stop('all') \n\n"
574 "before you continue";
575 return false;
576 }
577
578 auto configData = MPListConfig::FromAron(dto);
579 isMPReady.store(false);
580 while (mpTaskRunning.load())
581 {
582 usleep(1000);
583 }
584
585 for (const auto& mp : configData.mpList)
586 {
587 if (rnsMap.find(mp.nodeSetName) == rnsMap.end())
588 {
589 ARMARX_WARNING << "You have to make sure the RobotNodeSet " << mp.nodeSetName
590 << " in your MP config "
591 << "corresponds to one of the RobotNodeSet in the controllers";
592 return false;
593 }
594 }
595 mpConfig = configData;
597
599 ARMARX_VERBOSE << "-- successfully updated MP config.";
600 return true;
601 }
602
603 bool
604 MPPool::resetMPsV1(const ::armarx::aron::data::dto::DictPtr& dto,
605 const std::map<std::string, VirtualRobot::RobotNodeSetPtr>& rnsMap,
606 const std::shared_ptr<common::coordination::Coordination>& coordinator)
607 {
608 const std::scoped_lock lock(mtx_mps);
609 if (not isFinishedAll())
610 {
611 ARMARX_WARNING << "MP is not finished yet, cannot reset MP\n"
612 "If you want to force reset, please call \n\n"
613 " ctrl->stop('all') \n\n"
614 "before you continue";
615 return false;
616 }
617
618 auto configData = MPListConfig::FromAron(dto);
619 isMPReady.store(false);
620 while (mpTaskRunning.load())
621 {
622 usleep(1000);
623 }
624
625 if (coordinator)
626 {
627 if (not coordinator->isInitialized())
628 {
629 usleep(1000);
630 ARMARX_WARNING << "Coordinator is not yet initialized.";
631 return false;
632 }
633 for (const auto& nodeSetName : coordinator->getNodesetList())
634 {
635 if (rnsMap.find(nodeSetName) == rnsMap.end())
636 {
638 << "Requested RobotNodeSet " << nodeSetName
639 << " by coordinator does not exist in the controller. MP won't be created!";
640 return false;
641 }
642 }
643 }
644 else
645 {
646 for (const auto& mp : configData.mpList)
647 {
648 if (rnsMap.find(mp.nodeSetName) == rnsMap.end())
649 {
650 ARMARX_WARNING << "You have to make sure the RobotNodeSet " << mp.nodeSetName
651 << " in your MP config "
652 << "corresponds to one of the RobotNodeSet in the controllers";
653 return false;
654 }
655 }
656 }
657 mpConfig = configData;
659
660 reInitMPInputOutputDataV1(rnsMap, coordinator);
661 ARMARX_VERBOSE << "-- successfully updated MP config.";
662 return true;
663 }
664
665 bool
666 MPPool::resetMPsV2(const ::armarx::aron::data::dto::DictPtr& dto,
667 const std::map<std::string, MPReInitData>& data)
668 {
669 const std::scoped_lock lock(mtx_mps);
670 if (not isFinishedAll())
671 {
672 ARMARX_WARNING << "MP is not finished yet, cannot reset MP\n"
673 "If you want to force reset, please call \n\n"
674 " ctrl->stop('all') \n\n"
675 "before you continue";
676 return false;
677 }
678
679 auto configData = MPListConfig::FromAron(dto);
680 isMPReady.store(false);
681 while (mpTaskRunning.load())
682 {
683 usleep(1000);
684 }
685
686 for (const auto& mp : configData.mpList)
687 {
688 if (data.find(mp.nodeSetName) == data.end())
689 {
690 ARMARX_WARNING << "You have to make sure the RobotNodeSet " << mp.nodeSetName
691 << " in your MP config "
692 << "corresponds to one of the RobotNodeSet in the controllers";
693 return false;
694 }
695 }
696 mpConfig = configData;
698
700 ARMARX_VERBOSE << "-- successfully updated MP config.";
701 return true;
702 }
703
705 MPPool::getMPConfig(const Ice::Current& /*iceCurrent*/)
706 {
707 return mpConfig.toAronDTO();
708 }
709
710 void
711 MPPool::reInitMPInputOutputDataV2(const std::map<std::string, MPReInitData>& data)
712 {
713 ARMARX_VERBOSE << "-- reconfigure MP: reinitialize the mp input output, as well as the rt "
714 "related buffer values";
715 int index = 0;
716 for (auto& mp : mps)
717 {
718 // const auto& nodeSetName = ;
719 // ARMARX_CHECK_EQUAL(nodeSetName, limb.at(nodeSetName)->kinematicChainName);
720 const auto& d = data.at(mp.second.mp->getNodeSetName());
721 const auto& role = mp.second.mp->getRole();
722 if (role == "taskspace" or role == "object")
723 {
724 ARMARX_CHECK_EQUAL(d.pos.size(), 7)
725 << "the task space pos must have 7 dimensions, got " << d.pos.size();
726 // ARMARX_CHECK_EQUAL(d.vel.size(), 6)
727 // << "the task space velocity must have 6 dimensions, got " << d.vel.size();
728 const Eigen::Matrix4f currentPose = common::vec7fToMat4f(d.pos);
729 ARMARX_VERBOSE << "---- (" << index << ") init input output data for "
730 << mp.second.mp->getMPName();
731 std::dynamic_pointer_cast<mp::TSMPInput>(mp.second.input)->pose = currentPose;
732 std::dynamic_pointer_cast<mp::TSMPInput>(mp.second.input)->vel.setZero();
733 std::dynamic_pointer_cast<mp::TSMPOutput>(mp.second.output)->pose = currentPose;
734 std::dynamic_pointer_cast<mp::TSMPOutput>(mp.second.output)->vel.setZero();
735 }
736 else if (role == "nullspace" or role == "hand")
737 {
738 ARMARX_VERBOSE << "---- (" << index << ") init input output data for "
739 << mp.second.mp->getMPName() << " with " << d.pos.size()
740 << " joints";
741 std::dynamic_pointer_cast<mp::JSMPInput>(mp.second.input)->angleRadian = d.pos;
742 std::dynamic_pointer_cast<mp::JSMPInput>(mp.second.input)->angularVel = d.vel;
743 std::dynamic_pointer_cast<mp::JSMPOutput>(mp.second.output)->angleRadian = d.pos;
744 std::dynamic_pointer_cast<mp::JSMPOutput>(mp.second.output)->angularVel = d.vel;
745 }
746 // else if (_mp.second.mp->getRole() == "hand")
747 // {
748 // ARMARX_VERBOSE << "---- (" << index << ") init input output data for "
749 // << _mp.second.mp->getMPName() << " with "
750 // << d.pos.size() << " joints";
751 // std::dynamic_pointer_cast<mp::JSMPInput>(_mp.second.input)->angleRadian = d.pos;
752 // std::dynamic_pointer_cast<mp::JSMPInput>(_mp.second.input)->angularVel = d.vel;
753 // std::dynamic_pointer_cast<mp::JSMPOutput>(_mp.second.output)->angleRadian = d.pos;
754 // std::dynamic_pointer_cast<mp::JSMPOutput>(_mp.second.output)->angularVel = d.vel;
755 // }
756 index++;
757 }
758 }
759
760 void
762 const std::map<std::string, VirtualRobot::RobotNodeSetPtr>& rnsMap)
763 {
764 ARMARX_VERBOSE << "-- reconfigure MP: reinitialize the mp input output, as well as the rt "
765 "related buffer values";
766 int index = 0;
767 for (auto& mp : mps)
768 {
769 // const auto& nodeSetName = ;
770 // ARMARX_CHECK_EQUAL(nodeSetName, limb.at(nodeSetName)->kinematicChainName);
771 const VirtualRobot::RobotNodeSetPtr& rns = rnsMap.at(mp.second.mp->getNodeSetName());
772
773 if (mp.second.mp->getRole() == "taskspace")
774 {
775 Eigen::Matrix4f currentPose = rns->getTCP()->getPoseInRootFrame();
776 ARMARX_VERBOSE << "---- (" << index << ") init input output data for "
777 << mp.second.mp->getMPName();
778 std::dynamic_pointer_cast<mp::TSMPInput>(mp.second.input)->pose = currentPose;
779 std::dynamic_pointer_cast<mp::TSMPInput>(mp.second.input)->vel.setZero();
780 std::dynamic_pointer_cast<mp::TSMPOutput>(mp.second.output)->pose = currentPose;
781 std::dynamic_pointer_cast<mp::TSMPOutput>(mp.second.output)->vel.setZero();
782 }
783 else if (mp.second.mp->getRole() == "nullspace")
784 {
785 ARMARX_VERBOSE << "---- (" << index << ") init input output data for "
786 << mp.second.mp->getMPName() << " with "
787 << rns->getJointValues().size() << " joints";
788 std::dynamic_pointer_cast<mp::JSMPInput>(mp.second.input)->angleRadian =
789 rns->getJointValuesEigen();
790 std::dynamic_pointer_cast<mp::JSMPInput>(mp.second.input)->angularVel =
791 Eigen::VectorXf::Zero(rns->getJointValues().size());
792 std::dynamic_pointer_cast<mp::JSMPOutput>(mp.second.output)->angleRadian =
793 rns->getJointValuesEigen();
794 std::dynamic_pointer_cast<mp::JSMPOutput>(mp.second.output)->angularVel =
795 Eigen::VectorXf::Zero(rns->getJointValues().size());
796 }
797 else if (mp.second.mp->getRole() == "hand")
798 {
799 ARMARX_VERBOSE << "---- (" << index << ") init input output data for "
800 << mp.second.mp->getMPName() << " with "
801 << rns->getJointValues().size() << " joints";
802 std::dynamic_pointer_cast<mp::JSMPInput>(mp.second.input)->angleRadian =
803 rns->getJointValuesEigen();
804 std::dynamic_pointer_cast<mp::JSMPInput>(mp.second.input)->angularVel =
805 Eigen::VectorXf::Zero(rns->getJointValues().size());
806 std::dynamic_pointer_cast<mp::JSMPOutput>(mp.second.output)->angleRadian =
807 rns->getJointValuesEigen();
808 std::dynamic_pointer_cast<mp::JSMPOutput>(mp.second.output)->angularVel =
809 Eigen::VectorXf::Zero(rns->getJointValues().size());
810 }
811 index++;
812 }
813 }
814
815 void
817 const std::map<std::string, VirtualRobot::RobotNodeSetPtr>& rnsMap,
818 const std::shared_ptr<common::coordination::Coordination>& coordinator)
819 {
820 ARMARX_VERBOSE << "-- reconfigure MP: reinitialize the mp input output, as well as the rt "
821 "related buffer values";
822 int index = 0;
823 for (auto& mp : mps)
824 {
825 const auto& role = mp.second.mp->getRole();
826 // const auto& nodeSetName = ;
827 // ARMARX_CHECK_EQUAL(nodeSetName, limb.at(nodeSetName)->kinematicChainName);
828
829 if (role == "taskspace")
830 {
831 const VirtualRobot::RobotNodeSetPtr& rns =
832 rnsMap.at(mp.second.mp->getNodeSetName());
833 const Eigen::Matrix4f currentPose = rns->getTCP()->getPoseInRootFrame();
834 ARMARX_VERBOSE << "---- (" << index << ") init input output data for "
835 << mp.second.mp->getMPName();
836 std::dynamic_pointer_cast<mp::TSMPInput>(mp.second.input)->pose = currentPose;
837 std::dynamic_pointer_cast<mp::TSMPInput>(mp.second.input)->vel.setZero();
838 std::dynamic_pointer_cast<mp::TSMPOutput>(mp.second.output)->pose = currentPose;
839 std::dynamic_pointer_cast<mp::TSMPOutput>(mp.second.output)->vel.setZero();
840 }
841 else if (role == "object")
842 {
843 ARMARX_CHECK_NOT_NULL(coordinator)
844 << "When MP role is object, the coordinator must be active";
845 ARMARX_CHECK(coordinator->isInitialized())
846 << "The coordinator must first be initialized.";
847
848 const auto& coord =
849 std::dynamic_pointer_cast<common::coordination::SyncCoordination>(coordinator);
850 const std::scoped_lock lock(coord->mtx_data_non_rt);
851 const Eigen::Matrix4f currentPose = coord->dataNonRt.targetPose;
852
853 std::dynamic_pointer_cast<mp::TSMPInput>(mp.second.input)->pose = currentPose;
854 std::dynamic_pointer_cast<mp::TSMPInput>(mp.second.input)->vel.setZero();
855 std::dynamic_pointer_cast<mp::TSMPOutput>(mp.second.output)->pose = currentPose;
856 std::dynamic_pointer_cast<mp::TSMPOutput>(mp.second.output)->vel.setZero();
857 }
858 else if (role == "nullspace" or role == "hand")
859 {
860 const VirtualRobot::RobotNodeSetPtr& rns =
861 rnsMap.at(mp.second.mp->getNodeSetName());
862 ARMARX_VERBOSE << "---- (" << index << ") init input output data for "
863 << mp.second.mp->getMPName() << " with "
864 << rns->getJointValues().size() << " joints";
865 std::dynamic_pointer_cast<mp::JSMPInput>(mp.second.input)->angleRadian =
866 rns->getJointValuesEigen();
867 std::dynamic_pointer_cast<mp::JSMPInput>(mp.second.input)->angularVel =
868 Eigen::VectorXf::Zero(rns->getJointValues().size());
869 std::dynamic_pointer_cast<mp::JSMPOutput>(mp.second.output)->angleRadian =
870 rns->getJointValuesEigen();
871 std::dynamic_pointer_cast<mp::JSMPOutput>(mp.second.output)->angularVel =
872 Eigen::VectorXf::Zero(rns->getJointValues().size());
873 }
874 else
875 {
876 ARMARX_WARNING << "MP of role " << role << " is not supported!";
877 }
878 index++;
879 }
880 }
881
882} // namespace armarx::control::common::mp
uint8_t index
constexpr T c
bool resetMPs(const ::armarx::aron::data::dto::DictPtr &dto, const std::map< std::string, VirtualRobot::RobotNodeSetPtr > &rnsMap)
Definition MPPool.cpp:565
bool resetMPsV2(const ::armarx::aron::data::dto::DictPtr &dto, const std::map< std::string, MPReInitData > &data)
Definition MPPool.cpp:666
void learnFromTrajs(const ::armarx::aron::data::dto::DictPtr &dict, const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:426
void setGoal(const DVec &goals, const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:493
void resume(const std::string &mpName="all", const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:324
void reconfigureMPs(const MPListConfig &mpListConfig)
Definition MPPool.cpp:97
bool resetMPsV1(const ::armarx::aron::data::dto::DictPtr &dto, const std::map< std::string, VirtualRobot::RobotNodeSetPtr > &rnsMap, const std::shared_ptr< common::coordination::Coordination > &coordinator)
Definition MPPool.cpp:604
std::recursive_mutex mtx_mps
Definition MPPool.h:147
Ice::Double getCanVal(const std::string &mpName, const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:539
bool isFinished(const std::string &mpName="all", const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:386
void updateMPConfig(const ::armarx::aron::data::dto::DictPtr &dto, const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:557
void learnFromCSV(const Ice::StringSeq &fileNames=std::vector< std::string >(), const Ice::Current &iceCurrent=Ice::emptyCurrent) override
setting
Definition MPPool.cpp:406
void createMPs(const MPListConfig &mpListConfig)
Definition MPPool.cpp:23
void setStartAndGoal(const DVec &starts, const DVec &goals, const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:498
DVec deserialize(const std::string &, const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:532
void stop(const std::string &mpName="all", const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:262
std::map< std::string, MPInputOutput > mps
Definition MPPool.h:146
void reInitMPInputOutputData(const std::map< std::string, VirtualRobot::RobotNodeSetPtr > &rnsMap)
Definition MPPool.cpp:761
MPListConfig mpConfig
this variable is only needed when constructing the MP instances, therefore you don't need to use trip...
Definition MPPool.h:153
void reInitMPInputOutputDataV2(const std::map< std::string, MPReInitData > &data)
Definition MPPool.cpp:711
void requestStop(const std::string &mpName="all", const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:237
void start(const std::string &mpName="all", const DVec &startVec=std::vector< double >(), const DVec &goalVec=std::vector< double >(), Ice::Double timeDuration=-1.0, const Ice::Current &iceCurrent=Ice::emptyCurrent) override
control
Definition MPPool.cpp:183
std::map< arondto::MPGroup, PhaseStopResult > phaseStops_
Definition MPPool.h:162
void setViaPoint(Ice::Double u, const DVec &viapoint, const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:509
void reset(const std::string &mpName="all", const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:355
void reInitMPInputOutputDataV1(const std::map< std::string, VirtualRobot::RobotNodeSetPtr > &rnsMap, const std::shared_ptr< common::coordination::Coordination > &coordinator)
Definition MPPool.cpp:816
std::atomic< bool > isMPReady
Definition MPPool.h:148
void set(const ::armarx::StringDoubleSeqMap &, const ::armarx::StringDoubleSeqMap &, const ::armarx::StringDoubleMap &, const ::Ice::Current &iceCurrent=::Ice::emptyCurrent) override
Definition MPPool.cpp:147
void pause(const std::string &mpName="all", const Ice::Current &iceCurrent=Ice::emptyCurrent) override
Definition MPPool.cpp:293
#define ARMARX_CHECK(expression)
Shortcut for ARMARX_CHECK_EXPRESSION.
#define ARMARX_CHECK_NOT_NULL(ptr)
This macro evaluates whether ptr is not null and if it turns out to be false it will throw an Express...
#define ARMARX_CHECK_EQUAL(lhs, rhs)
This macro evaluates whether lhs is equal (==) rhs and if it turns out to be false it will throw an E...
#define ARMARX_INFO
The normal logging level.
Definition Logging.h:181
#define ARMARX_ERROR
The logging level for unexpected behaviour, that must be fixed.
Definition Logging.h:196
#define ARMARX_WARNING
The logging level for unexpected behaviour, but not a serious problem.
Definition Logging.h:193
#define ARMARX_VERBOSE
The logging level for verbose information.
Definition Logging.h:187
armarx::aron::data::dto::Dict getMPConfig()
string serialize()
serialze
::IceInternal::Handle< Dict > DictPtr
This file is part of ArmarX.
std::shared_ptr< TSMPOutput > TSMPOutputPtr
Definition TSMP.h:47
std::shared_ptr< KeypointsMPInput > KeypointsMPInputPtr
Definition KeypointsMP.h:45
Ice::DoubleSeq DVec
Definition MP.h:53
std::shared_ptr< TSMPInput > TSMPInputPtr
Definition TSMP.h:46
std::shared_ptr< JSMPOutput > JSMPOutputPtr
Definition JSMP.h:48
std::shared_ptr< KeypointsMPOutput > KeypointsMPOutputPtr
Definition KeypointsMP.h:46
std::shared_ptr< TSMP > TSMPPtr
Definition TSMP.h:67
std::shared_ptr< JSMP > JSMPPtr
Definition JSMP.h:61
std::shared_ptr< JSMPInput > JSMPInputPtr
Definition JSMP.h:47
std::shared_ptr< KeypointsMP > KeypointsMPPtr
Definition KeypointsMP.h:57
Eigen::Matrix4f vec7fToMat4f(const Eigen::VectorXf &vec)
Definition utils.cpp:340