28
28
// 3. testClutchedPathSpring()
29
29
// 4. testMcKibbenActuator()
30
30
// 5. testActuatorsCombination()
31
- //
31
+ // 6. testActivationCoordinateActuator()
32
+ //
32
33
// Add tests here as Actuators are added to OpenSim
33
34
//
34
35
// =============================================================================
@@ -55,6 +56,7 @@ void testBodyActuator();
55
56
void testClutchedPathSpring ();
56
57
void testMcKibbenActuator ();
57
58
void testActuatorsCombination ();
59
+ void testActivationCoordinateActuator ();
58
60
59
61
60
62
int main ()
@@ -81,6 +83,10 @@ int main()
81
83
catch (const std::exception& e) {
82
84
cout << e.what () << endl; failures.push_back (" testActuatorsCombination" );
83
85
}
86
+ try { testActivationCoordinateActuator (); }
87
+ catch (const std::exception& e) {
88
+ cout << e.what () << endl; failures.push_back (" testActivationCoordinateActuator" );
89
+ }
84
90
if (!failures.empty ()) {
85
91
cout << " Done, with failure(s): " << failures << endl;
86
92
return 1 ;
@@ -709,7 +715,7 @@ void testBodyActuator()
709
715
// ==================================================================================
710
716
/* *
711
717
* This test verifies if using a BodyActuator generates equivalent result in the body
712
- * acceleration compared to when using a combination of PointActuaor, TorqueActuaor
718
+ * acceleration compared to when using a combination of PointActuaor, TorqueActuator
713
719
* and BodyActuator.
714
720
* It therefore also verifies model consistency when user defines and uses a
715
721
* combination of these 3 actuators.
@@ -918,3 +924,46 @@ void testActuatorsCombination()
918
924
std::cout << " ********** Test Actuator Combination time = ********** " <<
919
925
1 .e3 *(std::clock () - startTime) / CLOCKS_PER_SEC << " ms\n " << endl;
920
926
}
927
+
928
+ // Test de/serialization and numerical integration of
929
+ // ActivationCoordinateActautor.
930
+ void testActivationCoordinateActuator () {
931
+ Model model;
932
+ auto * body = new Body (" body" , 1 , SimTK::Vec3 (0 ), SimTK::Inertia (0 ));
933
+ auto * joint = new PinJoint (" joint" , *body, model.getGround ());
934
+ joint->updCoordinate ().setName (" coord" );
935
+ model.addBody (body);
936
+ model.addJoint (joint);
937
+ auto * aca = new ActivationCoordinateActuator (" coord" );
938
+ aca->setName (" aca" );
939
+ const double a0 = 0.7 ;
940
+ const double tau = 0.20 ;
941
+ aca->set_default_activation (a0);
942
+ aca->set_activation_time_constant (tau);
943
+ model.addForce (aca);
944
+ model.finalizeFromProperties ();
945
+ model.finalizeConnections ();
946
+ model.print (" Model_ActivationCoordinateActuator.osim" );
947
+
948
+ Model modelDeserialized (" Model_ActivationCoordinateActuator.osim" );
949
+ ASSERT (model == modelDeserialized);
950
+
951
+ auto * controller = new PrescribedController ();
952
+ controller->addActuator (*aca);
953
+ const double x = 0.15 ;
954
+ controller->prescribeControlForActuator (" aca" , new Constant (x));
955
+ model.addController (controller);
956
+
957
+ auto state = model.initSystem ();
958
+
959
+ Manager manager (model);
960
+ manager.initialize (state);
961
+ const double tf = 0.10 ;
962
+ state = manager.integrate (tf);
963
+
964
+ const double expectedFinalActivation =
965
+ (a0 - x) * exp (-tf / tau) + x;
966
+ const double foundFinalActivation =
967
+ aca->getStateVariableValue (state, " activation" );
968
+ ASSERT_EQUAL (expectedFinalActivation, foundFinalActivation, 1e-4 );
969
+ }
0 commit comments