Skip to content

Commit d838a9b

Browse files
mitiguysherm1
andauthored
Compute composite mass properties (#24654)
Co-authored-by: Michael Sherman <sherm1@gmail.com>
1 parent 7605418 commit d838a9b

17 files changed

Lines changed: 1096 additions & 238 deletions

bindings/generated_docstrings/multibody_plant.h

Lines changed: 59 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -3752,7 +3752,7 @@ method computes:
37523752
where ``M(q)`` is the model's mass matrix (including rigid body mass
37533753
properties and reflected_inertia "reflected inertias"), ``C(q, v)v``
37543754
is the bias term for Coriolis and gyroscopic effects and ``tau_app``
3755-
consists of a vector applied generalized forces. The last term is a
3755+
consists of a vector of applied generalized forces. The last term is a
37563756
summation over all bodies in the model where ``Fapp_Bo_W`` is an
37573757
applied spatial force on body B at ``Bo`` which gets projected into
37583758
the space of generalized forces with the transpose of ``Jv_V_WB(q)``
@@ -5011,7 +5011,7 @@ be used by Finalize(); post-finalize it returns the joint type that
50115011
*was* used if there were any base bodies in need of a joint.
50125012
50135013
See also:
5014-
SetBaseBodyJointType(), Finalize())""";
5014+
SetBaseBodyJointType(), GetCombineWeldedBodies(), Finalize())""";
50155015
} GetBaseBodyJointType;
50165016
// Symbol: drake::multibody::MultibodyPlant::GetBodiesKinematicallyAffectedBy
50175017
struct /* GetBodiesKinematicallyAffectedBy */ {
@@ -5168,6 +5168,25 @@ geometries for ``body`` previously registered with a SceneGraph.
51685168
See also:
51695169
RegisterCollisionGeometry(), Finalize())""";
51705170
} GetCollisionGeometriesForBody;
5171+
// Symbol: drake::multibody::MultibodyPlant::GetCombineWeldedBodies
5172+
struct /* GetCombineWeldedBodies */ {
5173+
// Source: drake/multibody/plant/multibody_plant.h
5174+
const char* doc =
5175+
R"""((Internal use only for now) Returns the global or a model_instance
5176+
setting for whether or not to combine welded RigidBody (Link)
5177+
elements.
5178+
5179+
Note:
5180+
This function can be called pre-Finalize() or post-Finalize().
5181+
5182+
Parameter ``model_instance``:
5183+
(optional). If this argument is missing or not recognized, returns
5184+
the global setting. Otherwise returns the setting for this
5185+
specific model_instance.
5186+
5187+
See also:
5188+
SetCombineWeldedBodies(), GetBaseBodyJointType(), Finalize())""";
5189+
} GetCombineWeldedBodies;
51715190
// Symbol: drake::multibody::MultibodyPlant::GetConstraintActiveStatus
51725191
struct /* GetConstraintActiveStatus */ {
51735192
// Source: drake/multibody/plant/multibody_plant.h
@@ -6641,8 +6660,45 @@ Parameter ``model_instance``:
66416660
RuntimeError if called after Finalize().
66426661
66436662
See also:
6644-
GetBaseBodyJointType(), Finalize())""";
6663+
GetBaseBodyJointType(), SetCombineWeldedBodies(), Finalize())""";
66456664
} SetBaseBodyJointType;
6665+
// Symbol: drake::multibody::MultibodyPlant::SetCombineWeldedBodies
6666+
struct /* SetCombineWeldedBodies */ {
6667+
// Source: drake/multibody/plant/multibody_plant.h
6668+
const char* doc =
6669+
R"""((Internal use only for now) Controls whether welded-together RigidBody
6670+
(Link) elements are to be combined into a single composite mobilized
6671+
body in the generated model. If so, those Weld joints will not be
6672+
modeled (i.e. will have no corresponding mobilizer) in the
6673+
post-Finalize() model and there will be fewer mobilized bodies and
6674+
modeled joints in the generated model than in the user's specification
6675+
of links and joints. Results for the original RigidBody (Link)
6676+
elements can still be obtained by name or BodyIndex, but no results
6677+
(in particular, no reaction forces) are available for the unmodeled
6678+
Weld joints.
6679+
6680+
You can set this flag globally or on a per-model instance basis. If
6681+
there is a setting for a joint's model instance then that setting is
6682+
used; otherwise, the global setting is used.
6683+
6684+
The default global setting for Drake is *not* to combine welded
6685+
RigidBody elements.
6686+
6687+
Parameter ``combine``:
6688+
Whether to combine welded-together bodies. This only affects a
6689+
particular model instance if the ``model_instance`` argument is
6690+
also provided, otherwise it sets the global value.
6691+
6692+
Parameter ``model_instance``:
6693+
(optional) if present, specifies a particular model instance to
6694+
which the ``combine`` argument applies.
6695+
6696+
Raises:
6697+
RuntimeError if called after Finalize().
6698+
6699+
See also:
6700+
GetCombineWeldedBodies(), SetBaseBodyJointType(), Finalize())""";
6701+
} SetCombineWeldedBodies;
66466702
// Symbol: drake::multibody::MultibodyPlant::SetConstraintActiveStatus
66476703
struct /* SetConstraintActiveStatus */ {
66486704
// Source: drake/multibody/plant/multibody_plant.h

bindings/generated_docstrings/multibody_tree.h

Lines changed: 33 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1956,14 +1956,14 @@ R"""(Returns the owning MultibodyPlant LeafSystem.
19561956
// Source: drake/multibody/tree/force_element.h
19571957
const char* doc =
19581958
R"""(A ForceElement allows modeling state and time dependent forces in a
1959-
MultibodyTree model. Examples of such forces are springs, dampers,
1959+
MultibodyPlant model. Examples of such forces are springs, dampers,
19601960
drag and gravity. Forces that depend on accelerations such as virtual
19611961
mass cannot be modeled with a ForceElement. This abstract class
19621962
provides an API that all force elements subclasses must implement in
19631963
order to be fully defined. These are:
19641964
19651965
- CalcAndAddForceContribution(): computes the force contribution of a force
1966-
element in a MultibodyTree model.
1966+
element in a MultibodyPlant model.
19671967
- CalcPotentialEnergy(): computes a force element potential energy
19681968
contribution.
19691969
- CalcConservativePower(): computes the power generated by conservative
@@ -1980,7 +1980,7 @@ model, different force elements may write into the array of spatial
19801980
forces ``F_B_W`` or the array of generalized forces ``tau``.
19811981
19821982
Parameter ``context``:
1983-
The context containing the state of the MultibodyTree model.
1983+
The context containing the state of the MultibodyPlant model.
19841984
19851985
Parameter ``pc``:
19861986
A position kinematics cache object already updated to be in sync
@@ -1995,7 +1995,7 @@ Parameter ``forces``:
19951995
output ``this`` force element adds its contribution into
19961996
``forces``. This method will abort if the ``forces`` pointer is
19971997
null or if the forces object is not compatible with ``this``
1998-
MultibodyTree, see MultibodyForces∷CheckInvariants().
1998+
MultibodyPlant, see MultibodyForces∷CheckInvariants().
19991999
20002000
Precondition:
20012001
The position kinematics ``pc`` must have been previously updated
@@ -2076,6 +2076,13 @@ parameters of this method. It assumes ``forces`` to be a valid pointer
20762076
to a MultibodyForces object compatible with the MultibodyTree model
20772077
owning ``this`` force element.
20782078
2079+
Note:
2080+
Although spatial forces are applied to *links*, it is the
2081+
responsibility of the implementation to shift those forces to the
2082+
mobilized bodies that the links follow. When we are combining
2083+
welded-together links into composites, there can be multiple links
2084+
on the same mobilized body.
2085+
20792086
Precondition:
20802087
The position kinematics ``pc`` must have been previously updated
20812088
with a call to CalcPositionKinematicsCache().
@@ -4596,16 +4603,16 @@ class documentation states that a Space-fixed (extrinsic) X-Y-Z
45964603
rotation with roll-pitch-yaw angles [q₀ q₁ q₂] is equivalent to a
45974604
Body-fixed (intrinsic) Z-Y-X rotation by yaw-pitch-roll angles [q₂ q₁
45984605
q₀]. In the context of "gimbal torques", the Body-fixed Z-Y-X rotation
4599-
sequence with angles [q₂ q₁ q₀] is physical meaningful as it produces
4600-
torques associated with successive frames in a gimbal as τ₂ 𝐀𝐳, τ₁ 𝐏𝐲,
4601-
τ₀ 𝐂𝐱, where each of 𝐀𝐳, 𝐏𝐲, 𝐂𝐱 are unit vectors associated with a
4602-
frame in the yaw-pitch-roll rotation sequence and 𝐏𝐲 is a unit vector
4603-
of the "pitch" intermediate frame. As described earlier, torque 𝐭 is
4604-
the moment of the bushing forces on frame C about Cp. Scalars tx, ty,
4605-
tz are defined so 𝐭 can be expressed ``𝐭 = [tx ty tz]ᴀ = tx 𝐀𝐱 + ty 𝐀𝐲
4606-
+ tz 𝐀𝐳``. As shown in code documentation, the relationship of [tx ty
4607-
tz] to [τ₀ τ₁ τ₂] was found by equating 𝐭's power to τ's power as 𝐭 ⋅
4608-
w_AC = τ ⋅ q̇.
4606+
sequence with angles [q₂ q₁ q₀] is physically meaningful as it
4607+
produces torques associated with successive frames in a gimbal as τ₂
4608+
𝐀𝐳, τ₁ 𝐏𝐲, τ₀ 𝐂𝐱, where each of 𝐀𝐳, 𝐏𝐲, 𝐂𝐱 are unit vectors associated
4609+
with a frame in the yaw-pitch-roll rotation sequence and 𝐏𝐲 is a unit
4610+
vector of the "pitch" intermediate frame. As described earlier, torque
4611+
𝐭 is the moment of the bushing forces on frame C about Cp. Scalars tx,
4612+
ty, tz are defined so 𝐭 can be expressed ``𝐭 = [tx ty tz]ᴀ = tx 𝐀𝐱 +
4613+
ty 𝐀𝐲 + tz 𝐀𝐳``. As shown in code documentation, the relationship of
4614+
[tx ty tz] to [τ₀ τ₁ τ₂] was found by equating 𝐭's power to τ's power
4615+
as 𝐭 ⋅ w_AC = τ ⋅ q̇.
46094616
46104617
46114618
.. raw:: html
@@ -5438,11 +5445,11 @@ that is added during Finalize() should set this flag to ``True``.)""";
54385445
struct /* MultibodyForces */ {
54395446
// Source: drake/multibody/tree/multibody_forces.h
54405447
const char* doc =
5441-
R"""(A class to hold a set of forces applied to a MultibodyTree system.
5442-
Forces can include generalized forces as well as body spatial forces.
5443-
MultibodyPlant∷CalcGeneralizedForces() can be used to compute the
5444-
*total* generalized force, combining generalized_forces() and
5445-
body_forces().)""";
5448+
R"""(Holds a set of forces applied to a MultibodyTree system. Forces can
5449+
include generalized forces as well as mobilized body (mobod) spatial
5450+
forces. MultibodyPlant∷CalcGeneralizedForces() can be used to compute
5451+
the *total* generalized force, combining generalized_forces() with the
5452+
generalized force equivalent of the body_forces().)""";
54465453
// Symbol: drake::multibody::MultibodyForces::AddInForces
54475454
struct /* AddInForces */ {
54485455
// Source: drake/multibody/tree/multibody_forces.h
@@ -5475,9 +5482,13 @@ abort.)""";
54755482
const char* doc_1args_model = R"""((Advanced) Tree overload.)""";
54765483
// Source: drake/multibody/tree/multibody_forces.h
54775484
const char* doc_2args_nb_nv =
5478-
R"""(Number of bodies and number of generalized velocities overload. This
5479-
constructor is useful for constructing the MultibodyForces structure
5480-
before a MultibodyPlant has been constructed.)""";
5485+
R"""((Advanced) Constructs a force object with a given number of mobilized
5486+
bodies and corresponding mobilities (number of generalized
5487+
velocities). This constructor may be useful for constructing the
5488+
MultibodyForces structure before a MultibodyPlant has been
5489+
constructed. However, this must be used cautiously since the number of
5490+
mobilized bodies and their mobilities are not known until after
5491+
Finalize().)""";
54815492
} ctor;
54825493
// Symbol: drake::multibody::MultibodyForces::SetZero
54835494
struct /* SetZero */ {

multibody/plant/BUILD.bazel

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -458,6 +458,15 @@ drake_cc_googletest(
458458
],
459459
)
460460

461+
drake_cc_googletest(
462+
name = "composite_test",
463+
deps = [
464+
":plant",
465+
"//common/test_utilities:eigen_matrix_compare",
466+
"//common/test_utilities:expect_throws_message",
467+
],
468+
)
469+
461470
drake_cc_googletest(
462471
name = "compliant_contact_manager_scalar_conversion_test",
463472
deps = [

multibody/plant/multibody_plant.cc

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1422,12 +1422,24 @@ void MultibodyPlant<T>::SetBaseBodyJointType(
14221422
mutable_tree().SetBaseBodyJointType(joint_type, model_instance);
14231423
}
14241424

1425+
template <typename T>
1426+
void MultibodyPlant<T>::SetCombineWeldedBodies(
1427+
bool combine, std::optional<ModelInstanceIndex> model_instance) {
1428+
mutable_tree().SetCombineWeldedBodies(combine, model_instance);
1429+
}
1430+
14251431
template <typename T>
14261432
BaseBodyJointType MultibodyPlant<T>::GetBaseBodyJointType(
14271433
std::optional<ModelInstanceIndex> model_instance) const {
14281434
return internal_tree().GetBaseBodyJointType(model_instance);
14291435
}
14301436

1437+
template <typename T>
1438+
bool MultibodyPlant<T>::GetCombineWeldedBodies(
1439+
std::optional<ModelInstanceIndex> model_instance) const {
1440+
return internal_tree().GetCombineWeldedBodies(model_instance);
1441+
}
1442+
14311443
template <typename T>
14321444
void MultibodyPlant<T>::Finalize() {
14331445
// After finalizing the base class, tree is read-only.

multibody/plant/multibody_plant.h

Lines changed: 49 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1759,11 +1759,39 @@ class MultibodyPlant final : public internal::MultibodyTreeSystem<T> {
17591759
/// @param[in] model_instance (optional) the index of the model instance to
17601760
/// which `joint_type` is to be applied.
17611761
/// @throws std::exception if called after Finalize().
1762-
/// @see GetBaseBodyJointType(), Finalize()
1762+
/// @see GetBaseBodyJointType(), SetCombineWeldedBodies(), Finalize()
17631763
void SetBaseBodyJointType(
17641764
BaseBodyJointType joint_type,
17651765
std::optional<ModelInstanceIndex> model_instance = {});
17661766

1767+
/// (Internal use only for now) Controls whether welded-together RigidBody
1768+
/// (Link) elements are to be combined into a single composite mobilized
1769+
/// body in the generated model. If so, those Weld joints will not be modeled
1770+
/// (i.e. will have no corresponding mobilizer) in the post-Finalize()
1771+
/// model and there will be fewer mobilized bodies and modeled joints in the
1772+
/// generated model than in the user's specification of links and joints.
1773+
/// Results for the original RigidBody (Link) elements can still be obtained
1774+
/// by name or BodyIndex, but no results (in particular, no reaction forces)
1775+
/// are available for the unmodeled Weld joints.
1776+
///
1777+
/// You can set this flag globally or on a per-model instance basis. If
1778+
/// there is a setting for a joint's model instance then that setting is
1779+
/// used; otherwise, the global setting is used.
1780+
///
1781+
/// The default global setting for Drake is _not_ to combine welded RigidBody
1782+
/// elements.
1783+
///
1784+
/// @param[in] combine Whether to combine welded-together bodies. This only
1785+
/// affects a particular model instance if the `model_instance` argument is
1786+
/// also provided, otherwise it sets the global value.
1787+
/// @param[in] model_instance (optional) if present, specifies a particular
1788+
/// model instance to which the `combine` argument applies.
1789+
///
1790+
/// @throws std::exception if called after Finalize().
1791+
/// @see GetCombineWeldedBodies(), SetBaseBodyJointType(), Finalize()
1792+
void SetCombineWeldedBodies(
1793+
bool combine, std::optional<ModelInstanceIndex> model_instance = {});
1794+
17671795
/// Returns the currently-set choice for base body joint type, either for
17681796
/// the global setting or for a specific model instance if provided.
17691797
/// If a model instance is provided for which no explicit choice has been
@@ -1772,10 +1800,22 @@ class MultibodyPlant final : public internal::MultibodyTreeSystem<T> {
17721800
/// This can be called any time -- pre-finalize it returns the joint type
17731801
/// that will be used by Finalize(); post-finalize it returns the joint type
17741802
/// that _was_ used if there were any base bodies in need of a joint.
1775-
/// @see SetBaseBodyJointType(), Finalize()
1803+
/// @see SetBaseBodyJointType(), GetCombineWeldedBodies(), Finalize()
17761804
BaseBodyJointType GetBaseBodyJointType(
17771805
std::optional<ModelInstanceIndex> model_instance = {}) const;
17781806

1807+
/// (Internal use only for now) Returns the global or a model_instance setting
1808+
/// for whether or not to combine welded RigidBody (Link) elements.
1809+
///
1810+
/// @note This function can be called pre-Finalize() or post-Finalize().
1811+
///
1812+
/// @param[in] model_instance (optional). If this argument is missing or
1813+
/// not recognized, returns the global setting. Otherwise returns the
1814+
/// setting for this specific model_instance.
1815+
/// @see SetCombineWeldedBodies(), GetBaseBodyJointType(), Finalize()
1816+
bool GetCombineWeldedBodies(
1817+
std::optional<ModelInstanceIndex> model_instance = {}) const;
1818+
17791819
/// This method must be called after all elements in the model (joints,
17801820
/// bodies, force elements, constraints, etc.) are added and before any
17811821
/// computations are performed.
@@ -4142,12 +4182,13 @@ class MultibodyPlant final : public internal::MultibodyTreeSystem<T> {
41424182
/// where `M(q)` is the model's mass matrix (including rigid body mass
41434183
/// properties and @ref reflected_inertia "reflected inertias"), `C(q, v)v` is
41444184
/// the bias term for Coriolis and gyroscopic effects and `tau_app` consists
4145-
/// of a vector applied generalized forces. The last term is a summation over
4146-
/// all bodies in the model where `Fapp_Bo_W` is an applied spatial force on
4147-
/// body B at `Bo` which gets projected into the space of generalized forces
4148-
/// with the transpose of `Jv_V_WB(q)` (where `Jv_V_WB` is B's spatial
4149-
/// velocity Jacobian in W with respect to generalized velocities v).
4150-
/// Note: B's spatial velocity in W can be written as `V_WB = Jv_V_WB * v`.
4185+
/// of a vector of applied generalized forces. The last term is a summation
4186+
/// over all bodies in the model where `Fapp_Bo_W` is an applied spatial
4187+
/// force on body B at `Bo` which gets projected into the space of
4188+
/// generalized forces with the transpose of `Jv_V_WB(q)` (where `Jv_V_WB`
4189+
/// is B's spatial velocity Jacobian in W with respect to generalized
4190+
/// velocities v). Note: B's spatial velocity in W can be written as `V_WB
4191+
/// = Jv_V_WB * v`.
41514192
///
41524193
/// This method does not compute explicit expressions for the mass matrix nor
41534194
/// for the bias term, which would be of at least `O(n²)` complexity, but it

0 commit comments

Comments
 (0)