motornet.muscles#

class motornet.muscle.CompliantTendonHillMuscle(min_activation=0.01, **kwargs)#

Bases: RigidTendonHillMuscle

This pre-built muscle class is an implementation of a Hill-type muscle model as detailed in [1]. Unlike its parent class, this class implements a full compliant tendon version of the model, as formulated in the reference article.

References

[1] Kistemaker DA, Wong JD, Gribble PL. The central nervous system does not minimize energy cost in arm movements. J Neurophysiol. 2010 Dec;104(6):2985-94. doi: 10.1152/jn.00483.2010. Epub 2010 Sep 8. PMID: 20884757.

Parameters:
  • min_activationFloat, the minimum activation value that this muscle can have. Any activation value lower than this value will be clipped.

  • **kwargs – All contents are passed to the parent Muscle class.

class motornet.muscle.MujocoHillMuscle(min_activation: float = 0.0, passive_forces: float = 1.0, tau_activation: float = 0.01, tau_deactivation: float = 0.04, **kwargs)#

Bases: Muscle

This pre-built muscle class is an implementation of a Hill-type muscle model as detailed in the MuJoCo documentation`[1]`. It is a rigid tendon Hill-type model.

References

[1] https://mujoco.readthedocs.io/en/stable/modeling.html#muscle-actuators

Parameters:
  • min_activationFloat, the minimum activation value that this muscle can have. Any activation value lower than this value will be clipped.

  • passive_forcesFloat, a scalar coefficient to tune the contribution of passive forces to the total force output.

  • **kwargs – All contents are passed to the parent Muscle class.

build(timestep, max_isometric_force, tendon_length, optimal_muscle_length, normalized_slack_muscle_length, lmin, lmax, vmax, fvmax)#

Build the muscle using arguments from the motornet.effector.Effector wrapper object. This should be called by the motornet.effector.Effector.add_muscle() method to build the muscle structure according to the parameters of that effector.

Parameters:
  • timestepFloat, the size of a single timestep in seconds.

  • max_isometric_forceFloat or list of float, the maximum amount of force (N) that this particular muscle can use. If several muscles are being built, then this should be a list containing as many elements as there are muscles.

  • tendon_lengthFloat or list of float, the tendon length (m) of the muscle(s). If several muscles are declared in the parent effector object, then this should be a list containing as many elements as there are muscles in that parent effector object.

  • optimal_muscle_lengthFloat or list of float, the optimal length (m) of the muscle(s). This defines the length at which the muscle will output the maximum amount of force given the same excitation. If several muscles are declared in the parent effector object, then this should be a list containing as many elements as there are muscles in that parent effector object.

  • normalized_slack_muscle_lengthFloat or list of float, the muscle length (m) past which the muscle(s) will start to developp passive forces. If several muscles are declared in the parent effector object, then this should be a list containing as many elements as there are muscles in that parent effector object.

  • lminFloat, lower bound on the operating range of the muscle length (normalized by its optimal length).

  • lmaxFloat, upper bound on the operating range of the muscle length (normalized by its optimal length).

  • vmaxFloat, shortening velocity at which muscle force drops to zero (normalized by its optimal length per sec).

  • fvmaxFloat, active force generated at saturating lengthening velocity, relative to its maximum isometric force.

class motornet.muscle.Muscle(input_dim: int = 1, output_dim: int = 1, min_activation: float = 0.0, tau_activation: float = 0.015, tau_deactivation: float = 0.05)#

Bases: Module

Base class for Muscle objects. If a effector contains several muscles, this object will contain all of those in a vectorized format, meaning for any given effector there will always be only one muscle object, regardless of the number of muscles wrapped around the skeleton.

The dimensionality of the muscle states produced by this object and subclasses will always be n_batches * n_timesteps * n_states * n_muscles.

Parameters:
  • input_dimInteger, the dimensionality of the drive input to the muscle. For instance, if the muscle is only driven by an excitation signal, then this value should be 1.

  • output_dimInteger, the dimensionality of the output. Since this object does not rely on a call method, but on an integrate() method, this is the dimensionality of the integrate() method’s output. The output of that method should be a muscle state, so output_dim is usually the number of states of the Muscle object class or subclass.

  • min_activationFloat, the minimum activation value that this muscle can have. Any activation value lower than this value will be clipped.

  • tau_activationFloat, the time constant for activation of the muscle. This is used for the Ordinary Differential Equation of the muscle activation method activation_ode().

  • tau_deactivationFloat, the time constant for deactivation of the muscle. This is used for the Ordinary Differential Equation of the muscle activation method activation_ode().

activation_ode(action, activation)#

Computes the new activation value of the (set of) muscle(s) according to the Ordinary Differential Equation shown in equations 1-2 in [1]. Note that this is incidentally the same activation function as used for the muscle actuators in MuJoCo [2].

References

[1] Thelen DG. Adjustment of muscle mechanics model parameters to simulate dynamic contractions in older adults. J Biomech Eng. 2003 Feb;125(1):70-7. doi: 10.1115/1.1531112. PMID: 12661198. [2] https://mujoco.readthedocs.io/en/stable/modeling.html#muscle-actuators

Parameters:
  • excitationFloat or list of float, the descending excitation drive to the muscle(s). If several muscles are declared in the parent effector object, then this should be a list containing as many elements as there are muscles in that parent effector object.

  • muscle_stateTensor, the muscle state that provides the initial activation value for the Ordinary Differential Equation.

Returns:

A tensor containing the updated activation values.

build(timestep, max_isometric_force, **kwargs)#

Build the muscle given parameters from the motornet.effector.Effector wrapper object. This should be called by the motornet.effector.Effector.add_muscle() method to build the muscle scructure according to the parameters of that effector.

Parameters:
  • timestepFloat, the size of a single timestep in seconds.

  • max_isometric_forceFloat or list of float, the maximum amount of force (N) that this particular muscle can use. If several muscles are being built, then this should be a list containing as many elements as there are muscles.

  • **kwargs – Optional keyword arguments. This allows for extra parameters to be passed in the build() method for a Muscle subclass, if needed.

clip_activation(a)#
get_initial_muscle_state(batch_size, geometry_state)#

Infers the muscle state matching a provided geometry state array.

Parameters:
  • batch_sizeInteger, the size of the batch passed in geometry state.

  • geometry_stateTensor, the geometry state array from which the matching initial muscle state is inferred.

Returns:

A tensor containing the initial muscle state matching the input geometry state array.

get_save_config()#

Gets the object instance’s configuration. This is the set of configuration entries that will be useful for any muscle objects or subclasses.

Returns:

  • A dictionary containing the muscle object’s name and state names.

integrate(dt, state_derivative, muscle_state, geometry_state)#

Performs one integration step for the muscle step.

Parameters:
  • dtFloat, size of the timestep in seconds for this integration step.

  • state_derivativeTensor, the derivatives of the muscle state. These are usually obtained using this object’s ode() method.

  • muscle_stateTensor, the muscle state used as the initial state value for the numerical integration.

  • geometry_stateTensor, the geometry state used as the initial state value for the numerical integration.

Returns:

A tensor containing the new muscle state following numerical integration.

ode(action, muscle_state)#

Computes the derivatives of muscle state using the corresponding Ordinary Differential Equations.

Parameters:
  • actionTensor, the descending excitation drive to the muscle(s).

  • muscle_stateTensor, the muscle state used as the initial value for the evaluation of the Ordinary Differential Equations.

Returns:

A tensor containing the derivatives of the muscle state.

setattr(name: str, value)#

Changes the value of an attribute held by this object.

Parameters:
  • nameString, attribute to set to a new value.

  • value – Value that the attribute should take.

class motornet.muscle.ReluMuscle(**kwargs)#

Bases: Muscle

A “rectified linear” muscle whose force output \(F\) is a linear function of its activation value, which itself is bounded between 0 and 1. Specifically:

\[F = m * activation\]

with \(m\) the maximum isometric force of the muscle. Note that the maximum isometric force is not declared at initialization but via the Muscle.build() call, which is inherited from the parent Muscle class. The \(activation\) value is the result of an Ordinary Differential Equation computed by the Muscle.activation_ode() method. It is not directly the action input drive.

Parameters:

**kwargs – All contents are passed to the parent Muscle class.

class motornet.muscle.RigidTendonHillMuscle(min_activation=0.001, **kwargs)#

Bases: Muscle

This pre-built muscle class is an implementation of a Hill-type muscle model as detailed in [1], adjusted to behave as a rigid tendon version of the original model.

References

[1] Kistemaker DA, Wong JD, Gribble PL. The central nervous system does not minimize energy cost in arm movements. J Neurophysiol. 2010 Dec;104(6):2985-94. doi: 10.1152/jn.00483.2010. Epub 2010 Sep 8. PMID: 20884757.

Parameters:
  • min_activationFloat, the minimum activation value that this muscle can have. Any activation value lower than this value will be clipped.

  • **kwargs – All contents are passed to the parent Muscle class.

build(timestep, max_isometric_force, tendon_length, optimal_muscle_length, normalized_slack_muscle_length)#

Build the muscle using arguments from the motornet.effector.Effector wrapper object. This should be called by the motornet.effector.Effector.add_muscle() method to build the muscle structure according to the parameters of that effector.

Parameters:
  • timestepFloat, the size of a single timestep in seconds.

  • max_isometric_forceFloat or list of float, the maximum amount of force (N) that this particular muscle can use. If several muscles are being built, then this should be a list containing as many elements as there are muscles.

  • tendon_lengthFloat or list of float, the tendon length (m) of the muscle(s). If several muscles are declared in the parent effector object, then this should be a list containing as many elements as there are muscles in that parent effector object.

  • optimal_muscle_lengthFloat or list of float, the optimal length (m) of the muscle(s). This defines the length at which the muscle will output the maximum amount of force given the same excitation. If several muscles are declared in the parent effector object, then this should be a list containing as many elements as there are muscles in that parent effector object.

  • normalized_slack_muscle_lengthFloat or list of float, the muscle length (m) past which the muscle(s) will start to developp passive forces. If several muscles are declared in the parent effector object, then this should be a list containing as many elements as there are muscles in that parent effector object.

class motornet.muscle.RigidTendonHillMuscleThelen(min_activation=0.001, **kwargs)#

Bases: Muscle

This pre-built muscle class is an implementation of a Hill-type muscle model as detailed in [1], adjusted to behave as a rigid tendon version of the original model.

References

[1] Thelen DG. Adjustment of muscle mechanics model parameters to simulate dynamic contractions in older adults. J Biomech Eng. 2003 Feb;125(1):70-7. doi: 10.1115/1.1531112. PMID: 12661198.

Parameters:
  • min_activationFloat, the minimum activation value that this muscle can have. Any activation value lower than this value will be clipped.

  • **kwargs – All contents are passed to the parent Muscle class.

build(timestep, max_isometric_force, tendon_length, optimal_muscle_length, normalized_slack_muscle_length)#

Build the muscle using arguments from the motornet.effector.Effector wrapper object. This should be called by the motornet.effector.Effector.add_muscle() method to build the muscle structure according to the parameters of that effector.

Parameters:
  • timestepFloat, the size of a single timestep in seconds.

  • max_isometric_forceFloat or list of float, the maximum amount of force (N) that this particular muscle can use. If several muscles are being built, then this should be a list containing as many elements as there are muscles.

  • tendon_lengthFloat or list of float, the tendon length (m) of the muscle(s). If several muscles are declared in the parent effector object, then this should be a list containing as many elements as there are muscles in that parent effector object.

  • optimal_muscle_lengthFloat or list of float, the optimal length (m) of the muscle(s). This defines the length at which the muscle will output the maximum amount of force given the same excitation. If several muscles are declared in the parent effector object, then this should be a list containing as many elements as there are muscles in that parent effector object.

  • normalized_slack_muscle_lengthFloat or list of float, the muscle length (m) past which the muscle(s) will start to developp passive forces. If several muscles are declared in the parent effector object, then this should be a list containing as many elements as there are muscles in that parent effector object.