r"""
Actuators are the interface by which an Agent moves in the World. The following description is summarized from
`Mujoco <https://mujoco.readthedocs.io/en/stable/computation.html#actuation-model>`__. The nomenclature is
summarized in the following table.
=========================================== ===============================================
Keyword Nomenclature
=========================================== ===============================================
Actuator index :math:`{}_i`
Actuator control input :math:`u_i`
Actuator force output :math:`p_i`
Actuator Length :math:`l_i(q)`
Joint position :math:`q`
Joint momentum arms for each Actuator :math:`\nabla l_i(q)`
Gain term :math:`\bf a`
Bias term :math:`\bf b`
Gain parameters :math:`\vec a`
Bias parameters :math:`\vec b`
Dynamics parameters :math:`\vec d`
=========================================== ===============================================
Force Transmission
==================
:class:`Actuators <BaseActuator>` enables :class:`Agents <blueprints.agent.Agent>` to move in the
:class:`World <blueprints.world.World>`. Each Actuator has a single control input :math:`u_i` and a single force
output :math:`p_i`. Additionally each Actuator has a scalar value called its length :math:`l_i(q)` which is a
function of the Joints position :math:`q` and is defined by the Actuators properties. The force of an
:class:`Actuator <BaseActuator>` acting on a :class:`Joint <blueprints.joints.BaseJoint>` is the Actuator force :math:`p`
distributed over the Joints degrees of freedoms by scaling them with the momentum arms :math:`\nabla l`. The
net force acting on a Joint than is:
:math:`\vec F = \sum_i \nabla l_i(q) \cdot p_i`
Force Generation
================
The force generated by an Actuator affacting a Joint is dependent on three variables, 'Actuator control input
:math:`u_i`, a dynamic activation state :math:`w_i` (for some Actuators) and the Actuator length for the Joint
:math:`l_i(q)` as well as its velocity :math:`\dot{l}_i(q)`. The force is generated from an affine
mapping with a linear gain term :math:`\bf a` and a bias term :math:`\bf b`.
:math:`p_i(u_i, w_i, l_i, \dot l_i) = \textbf {a} (l_i, \dot l_i) \cdot (u_i \text{ or } w_i) + \textbf {b} (l_i, \dot l_i)`
Gain
----
The gain term :math:`\bf a` is linear w.r.t. either the control output :math:`u_i` or the activation variable
:math:`w_i` which dynamically depends on :math:`u_i` and will be explained in a later section. The activation
dynamics are defined in :attr:`dyntype <BaseActuator.dyntype>`. The gain term is computed by one of the
following options, which can be specified in :attr:`gaintype <BaseActuator.gaintype>` and the respective gain
parameters :math:`\vec a` are defined in :attr:`gainprm <BaseActuator.gainprm>`.
======================================== ===============================================
:attr:`gaintype <BaseActuator.gaintype>` :math:`\textbf{a}(l_i, \dot l_i)`
======================================== ===============================================
``'fixed'`` :math:`\textbf{a} = a_0`
``'affine'`` :math:`\textbf{a} = a_0 + a_1 \cdot l_i + a_2 \cdot \dot l_i`
``'muscle'`` :math:`\textbf{a} = \text{muscle_gain}(…)`
``'user'`` :math:`\textbf{a} = \text{user_gain}(…)`
======================================== ===============================================
A description for muscle dynamics can be found `here <https://mujoco.readthedocs.io/en/latest/modeling.html#cmuscle>`__.
Bias
----
The bias term is a constant added to the Actuator force and does not depend on the Actuator outputs. The bias
term is computed by one of the following options, which can be specified in :attr:`biastype <BaseActuator.biastype>`
and the respective bias parameters :math:`\vec b` are defined in :attr:`biasprm <BaseActuator.biasprm>`.
======================================== ===============================================
:attr:`biastype <BaseActuator.biastype>` :math:`\textbf{b}(l_i, \dot l_i)`
======================================== ===============================================
``'none'`` :math:`\textbf{b} = 0`
``'affine'`` :math:`\textbf{b} = b_0 + b_1 \cdot l_i + b_2 \cdot \dot l_i`
``'muscle'`` :math:`\textbf{b} = \text{muscle_bias}(…)`
``'user'`` :math:`\textbf{b} = \text{user_bias}(…)`
======================================== ===============================================
A description for muscle dynamics can be found `here <https://mujoco.readthedocs.io/en/latest/modeling.html#cmuscle>`__.
Activation
----------
Some Actuators use an activation variable :math:`\textbf{w}` instead of the control variable :math:`\textbf{u}`
to compute :math:`\textbf{a}`. The activation dynamics are specified in :attr:`dyntype <BaseActuator.dyntype>`
and the respective dynamics parameters :math:`\vec d` are defined in :attr:`dynprm <BaseActuator.dynprm>`.
====================================== ===================================================== ==========================================================
:attr:`dyntype <BaseActuator.dyntype>` Force Generation :math:`p_i(u_i, w_i, l_i, \dot l_i)` Activation dynamics :math:`w_i`
====================================== ===================================================== ==========================================================
``'none'`` :math:`p_i = \textbf{a} \cdot u_i + \textbf{b}` No internal state
``'integrator'`` :math:`p_i = \textbf{a} \cdot w_i + \textbf{b}` :math:`\dot w = u`
``'filter'`` :math:`p_i = \textbf{a} \cdot w_i + \textbf{b}` :math:`\dot w = (u - w)/d_0`
``'filterexact'`` :math:`p_i = \textbf{a} \cdot w_i + \textbf{b}` like filter but with exact integration
``'muscle'`` :math:`p_i = \textbf{a} \cdot w_i + \textbf{b}` :math:`\dot w = \text{muscle_dyn}(…)`
``'user'`` :math:`p_i = \textbf{a} \cdot w_i + \textbf{b}` :math:`\dot w = \text{user_dyn}(…)`
====================================== ===================================================== ==========================================================
A description for muscle dynamics can be found `here <https://mujoco.readthedocs.io/en/latest/modeling.html#cmuscle>`__.
Usage
=====
Actuators can either be defined using the :class:`General` Actuator, or by using one of the shortcut Actuators —
:class:`Motor`, :class:`Position`, :class:`Velocity`, :class:`IntVelocity`, :class:`Damper`, :class:`Cylinder`,
:class:`Muscle` and :class:`Adhesion`.
Attachment
----------
Actuators will apply a force to their parent. They can be attached to :class:`Bodies <blueprints.body.Body>`,
:class:`Joints <blueprints.joints.BaseJoint>` and :class:`Sites <blueprints.sites.BaseSite>`.
.. code-block:: python
:caption: Attachment to Parents
>>> actuator = blue.actuators.General()
>>> body = blue.Body(actuators=actuator)
>>> joint = blue.joints.Joint(actuators=actuator)
>>> site = blue.sites.Site(actuators=actuator)
For the force computation an Actuator that is attached to a :class:`Joint <blueprints.joints.BaseJoint>` can
also use the joints parent frame of reference by setting the :attr:`inparent <BaseActuator.inparent>` argument.
.. code-block:: python
:caption: Joint in parent
>>> actuator = blue.actuators.General(inparent=True)
>>> joint = blue.joints.Joint(actuators=actuator)
:class:`Sites <blueprints.sites.BaseSite>` can also use a different frame of reference using either the
:attr:`refsite <BaseActuator.refsite>` or the :attr:`ref_actuators <blueprints.sites.BaseSite.ref_actuators>`
attribute. This can only be done for Sites that are part of the same kinematic tree.
Reference Sites
---------------
.. code-block:: python
:caption: Reference Sites Error
:emphasize-lines: 5
>>> source = blue.sites.Site(name='source')
>>> target = blue.sites.Site(name='target')
>>> source.attach(actuator)
>>> target.ref_actuators = source.actuators
ValueError: Setting refsite is only allowed for references that share the same root.
Setting reference :class:`Sites <blueprints.sites.BaseSite>` can either be done, by setting the
:attr:`ref_actuators <blueprints.sites.BaseSite.ref_actuators>` or the :attr:`refsite <BaseActuator.refsite>`
attribute.
.. code-block:: python
:caption: Reference Sites Variations
>>> root = blue.Body(sites=[source, target])
VARIATION 1
>>> root.sites['target'].ref_actuators = root.sites['source'].actuators
VARIATION 2
>>> root.sites['source'].actuators.refsite = root.sites['target']
The resulting XML looks like this:
.. code-block:: mxml
:caption: XML Structure Attachment
<mujoco>
<actuator>
<general name="unnamed_general" refsite="target" site="source" />
</actuator>
<worldbody>
<body name="root">
<site type="site" name="source" />
<site type="site" name="target" />
</body>
</worldbody>
</mujoco>
Detachment
----------
When the parent Site or the reference Site are no longer part of the same kinematic tree, the reference Site
gets detached. This is necessary to avoid redundant copies of Actuators of orphaned parents and references.
.. code-block:: python
:caption: Reference Sites Detachment
>>> root.sites['source'].actuators.refsite
View[1|root.sites.actuators.refsite]
>>> root.detach(root.sites['target'])
>>> root.sites['source'].actuators.refsite
[]
The resulting XML looks like this:
.. code-block:: mxml
:caption: XML Structure Detachment
<mujoco>
<actuator>
<general name="unnamed_general" site="source" />
</actuator>
<worldbody>
<body name="root">
<site type="site" name="source" />
</body>
</worldbody>
</mujoco>
.. code-block:: python
:caption: Parent Sites Detachment
>>> root.sites['source'].actuators.refsite
View[1|root.sites.actuators.refsite]
>>> root.detach(root.sites['source'])
>>> root.sites['target'].ref_actuators
View[0|root.sites.ref_actuators]
The resulting XML looks like this:
.. code-block:: mxml
:caption: XML Structure Detachment
<mujoco>
<worldbody>
<body name="root">
<site type="site" name="target" />
</body>
</worldbody>
</mujoco>
.. note::
Actuators will not appear as children of their parents in xml, but instead in a separate ``<actuators>`` element.
"""
import xml.etree.ElementTree as xml
import numpy as np
import blueprints as blue
[docs]
class BaseActuator(blue.ActuatorType, blue.CyclicalThing, blue.NodeThing):
"""
Most attribute descriptions are partially taken from `Mujoco <https://mujoco.readthedocs.io/en/latest/XMLreference.html#actuator>`__.
"""
[docs]
@blue.restrict
def __init__(self,
name: str|None = None,
inparent: bool = False,
ctrllimited: bool|None = None,
forcelimited: bool|None = None,
actlimited: bool|None = None,
ctrlrange: list[int|float]|np.ndarray = [0., 0.],
forcerange: list[int|float]|np.ndarray = [0., 0.],
actrange: list[int|float]|np.ndarray = [0., 0.],
lengthrange: list[int|float]|np.ndarray = [0., 0.],
gear: int|float|list[int|float]|np.ndarray = [1., 0., 0., 0., 0., 0.],
cranklength: int|float|list[int|float]|np.ndarray = 0.,
dyntype: str = 'none',
gaintype: str = 'fixed',
biastype: str = 'none',
dynprm: int|float|list[int|float]|np.ndarray = 1.,
gainprm: int|float|list[int|float]|np.ndarray = 1.,
biasprm: int|float|list[int|float]|np.ndarray = 1.,
sensors: list|blue.SensorType|None = None,
copy: bool = True,
**kwargs):
"""
Parameters
----------
name : str | None, optional
The user specified name for the Actuator. In the case of a naming conflict the name will
be altered by an enumeration scheme.
inparent : bool, optional
If`:attr:`inparent` is True and the parent of the Actuator is :class:`blueprints.joints.BaseJoint`
the actuator assumes the frame of reference from the parent.
ctrllimited : bool | None, optional
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
forcelimited : bool | None, optional
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled
actlimited : bool | None, optional
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
ctrlrange : np.ndarray | list[int | float], optional
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
forcerange : np.ndarray | list[int | float], optional
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
actrange : np.ndarray | list[int | float], optional
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
lengthrange : np.ndarray | list[int | float], optional
Range of feasible lengths of the actuator’s transmission.
gear : np.ndarray | list[int | float], optional
This attribute scales the length (and consequently moment arms, velocity and force) of
the actuator, for all transmission types. It is different from the gain in the force
generation mechanism, because the gain only scales the force output and does not affect
the length, moment arms and velocity. For actuators with scalar transmission, only the
first element of this vector is used. The remaining elements are needed for joint (with
or without inparent) and site transmissions where this attribute is used to specify 3D
force and torque axes.
cranklength : int | float, optional
Used only for the slider-crank transmission type. Specifies the length of the connecting
rod. The compiler expects this value to be positive when a slider-crank transmission is
present.
dyntype : str, optional
Activation dynamics type for the actuator.
================= ===============================================
Keyword Description
================= ===============================================
``'none'`` No internal state
``'integrator'`` :math:`\\dot w = u`
``'filter'`` :math:`\\dot w = (u - w)/\\text{dynprm}[0]`
``'filterexact'`` Like filter but with exact integration
``'muscle'`` :math:`\\dot w = \\text{mju_muscleDynamics}(…)`
``'user'`` :math:`\\dot w = \\text{mjcb_act_dyn}(…)`
================= ===============================================
gaintype : str, optional
The gain and bias together determine the output of the force generation mechanism, which is
currently assumed to be affine. As already explained :attr:`above <blueprints.actuators.__doc__>`, the general formula
is: :math:`p = \\textbf{a} \\cdot (u \\text{ or } w) + \\textbf{b}`
The formula uses the activation state when present, and the control otherwise. The keywords
have the following meaning:
================= ===============================================
Keyword Description
================= ===============================================
``'fixed'`` :math:`\\textbf{a} = a_0`
``'affine'`` :math:`\\textbf{a} = a_0 + a_1 \\cdot length + a_2 \\cdot velocity`
``'muscle'`` :math:`\\textbf{a} = \\text{mju_muscleGain}(…)`
``'user'`` :math:`\\textbf{a} = \\text{mjcb_act_gain}(…)`
================= ===============================================
biastype : str, optional
The keywords have the following meaning:
================= ===============================================
Keyword Description
================= ===============================================
``'none'`` :math:`\\textbf{b} = 0`
``'affine'`` :math:`\\textbf{b} = b_0 + b_1 \\cdot length + b_2 \\cdot velocity`
``'muscle'`` :math:`\\textbf{b} = \\text{mju_muscleBias}(…)`
``'user'`` :math:`\\textbf{b} = \\text{mjcb_act_bias}(…)`
================= ===============================================
dynprm : int | float | list[int | float] | np.ndarray, optional
Activation dynamics parameters. The built-in activation types (except for muscle) use only the
first parameter, but we provide additional parameters in case user callbacks implement a more
elaborate model. The length of this array is not enforced by the parser, so the user can enter
as many parameters as needed. These defaults are not compatible with muscle actuators.
gainprm : int | float | list[int | float] | np.ndarray, optional
Gain parameters. The built-in gain types (except for muscle) use only the first parameter, but
we provide additional parameters in case user callbacks implement a more elaborate model. The
length of this array is not enforced by the parser, so the user can enter as many parameters as
needed. These defaults are not compatible with muscle actuators.
biasprm : int | float | list[int | float] | np.ndarray, optional
Bias parameters. The affine bias type uses three parameters. The length of this array is not
enforced by the parser, so the user can enter as many parameters as needed. These defaults are
not compatible with muscle actuators.
sensors : list | blue.SensorType | None, optional
The Sensors are attached to the actuator on initialization.
copy : bool, optional
If True, the Sensors passed during init will be copied before attachment, otherwise the original
Sensor is attached.
**kwargs
Keyword arguments are passed to ``super().__init__``.
"""
if isinstance(gear, (int, float)):
gear = [float(gear), 0., 0., 0., 0., 0.]
# MUJOCO PROPERTIES
self.ctrllimited = ctrllimited
self.forcelimited = forcelimited
self.actlimited = actlimited
self.ctrlrange = ctrlrange
self.forcerange = forcerange
self.actrange = actrange
self.lengthrange = lengthrange
self.gear = gear
self.cranklength = cranklength
self.dyntype = dyntype
self.gaintype = gaintype
self.biastype = biastype
self.dynprm = dynprm
self.gainprm = gainprm
self.biasprm = biasprm
self.inparent = inparent
# PARENT PROPERTIES
pack = lambda x: x if isinstance(x, list) else [x]
sensors = pack(sensors) if sensors else []
self._sensors = []
self._CHILDREN = {'sensors': {'type': blue.SensorType,
'children': self._sensors}}
self._tag = None
super().__init__(name=name,
**kwargs)
self.attach(*sensors,
copy=copy)
self._check_children_types()
@blue.restrict
def _build(self, parent, world, indicies, **kwargs):
"""
This method is called by the Actuators parent to construct the xml representations of
the kinematic tree. It recursively calls the :meth:`blueprints.sensors.BaseSensor._build`
methods if its sensor children.
Parameters
----------
parent : xml.etree.ElementTree.Element
The xml element of its parent
world : WorldType
The World from which the build method was called initially
**kwargs
Keyword arguments are overwrite the mujoco specs for building.
Returns
-------
xml.etree.ElementTree.Element
The built xml element of the Actuator.
"""
self._force_index = indicies['force']
indicies['force'] += 1
if self.dyntype != 'none':
self._activation_index = indicies['activation']
indicies['activation'] += 1
specs = self._mujoco_specs(kwargs)
if self.parent_tag == 'joints' and self.inparent:
specs['jointinparent'] = self.parent.name
else:
if self.refsite is not None:
specs['refsite'] = self.refsite.name
specs[self.parent_tag] = self.parent.name
self._xml_root = xml.SubElement(world._xml_actuator,
self.tag,
**specs)
self._build_children(parent=self._xml_root,
world=world,
indicies=indicies)
return self._xml_root
@property
def force(self) -> float:
"""
The force applied to the Actuator
Returns
-------
float
"""
if not hasattr(self, '_force_index'):
raise Exception('Actuator must first be build by a World before forces are available.')
else:
return float(self.root._mj_data.ctrl[self._force_index])
@force.setter
@blue.restrict
def force(self, force: int|float|np.float16|np.float32|np.float64) -> None:
"""
Parameters
----------
force : int | float | np.float
The force which is to be applied to the Actuator
"""
if not hasattr(self, '_force_index'):
raise Exception('Actuator must first be build by a World before forces are available.')
else:
force = float(force)
if force < self.ctrlrange[0]:
force = self.ctrlrange[0]
elif force > self.ctrlrange[1]:
force = self.ctrlrange[1]
self.root._mj_data.ctrl[self._force_index] = force
@property
def activation(self) -> float|None:
"""
The activation state of the Actuator
Returns
-------
float
"""
if not hasattr(self, '_force_index'):
raise Exception('Actuator must first be build by a World before activations are available.')
elif self.dyntype == 'none':
return None
else:
return float(self.root._mj_data.act[self._activation_index])
@activation.setter
@blue.restrict
def activation(self, activation: int|float|np.float16|np.float32|np.float64) -> None:
"""
Parameters
----------
activation : int | float | np.float
The activation which is to be applied to the Actuator
"""
if not hasattr(self, '_force_index'):
raise Exception('Actuator must first be build by a World before activations are available.')
if self.dyntype == 'none':
raise Exception('Actuators of dyntype "none" cannot be used for activations. See :class:`Actuators` for a detailed explanation.')
else:
self.root._mj_data.act[self._activation_index] = float(activation)
def __str__(self) -> str:
"""
The xml representation of the Actuator
Returns
-------
str
"""
specs = self._mujoco_specs()
if self.parent_tag == 'joints' and self.inparent:
specs['jointinparent'] = self.parent.name
else:
if self.refsite is not None:
specs['refsite'] = self.refsite.name
specs[self.parent_tag] = self.parent.name
xml_element = xml.Element(self.tag, **specs)
return xml.tostring(xml_element, encoding='unicode')
# XML PROPERTIES
@blue.restrict
@classmethod
def _from_xml_element(cls,
xml_element: xml.Element,
sensor: blue.SensorType|None = None) -> blue.ThingType:
"""
This method reconstructs an Actuator from an xml element.
Parameters
----------
xml_element : xml.Element
The xml element from which a Mesh is reconstructed.
sensor : blue.AssetType
The Sensor which is attached to the Actuator.
Returns
-------
blue.ThingType
The reconstructed Actuator.
"""
init_args, post_args, rest_args = cls._xml_element_args(xml_element)
init_args['sensors'] = sensor
init_args['copy'] = False
actuator_type = xml_element.tag
actuator = object.__new__(blue.REGISTER.ACTUATOR_THINGS[actuator_type])
actuator.__init__(**init_args)
for key, val in post_args.items():
setattr(actuator, key, val)
return actuator
# PARENT PROPERTIES
@property
def parent_tag(self):
"""
The name of the parent that is used for the reference attribute in the xml tag.
Returns
-------
str
A string describing the parent tag
Raises
------
ValueError
If the parent is not of a valid ThingType an error is raised.
"""
if self.parent is None:
return None
elif isinstance(self.parent, blue.JointType):
return 'joint'
elif isinstance(self.parent, blue.SiteType):
return 'site'
elif isinstance(self.parent, blue.BodyType):
return 'body'
else:
raise ValueError(f'Parent attribute is not Joint, Site or Body but {type(self.parent)}.')
@property
def inparent(self) -> bool:
"""
If ``inparent`` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
Returns
-------
bool
"""
return self._inparent
@inparent.setter
@blue.restrict
def inparent(self, inparent: bool) -> None:
"""
If ``inparent`` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
Parameters
----------
inparent : bool
indicates whether the reference frame is taken from the parent Joint
"""
self._inparent = inparent
@property
def refsite(self) -> blue.SiteType|None:
"""
If refsite is set to a side, the Actuator will assume the frame of reference of the refsite
instead of its parent. This only possible if the parent is also a :class:`Site <blueprints.sites.BaseSite>`.
Returns
-------
blue.SiteType | None
"""
if hasattr(self, '_refsite'):
return self._refsite
else:
return None
@refsite.setter
@blue.restrict
def refsite(self, refsite: blue.SiteType|None) -> None:
"""
If refsite is set to a side, the Actuator will assume the frame of reference of the refsite
instead of its parent. This only possible if the parent is also a :class:`Site <blueprints.sites.BaseSite>`.
Parameters
----------
refsite : blue.SiteType | None
blue.SiteType | None
Raises
------
ValueError
If the parent is not a :class:`Site <blueprints.sites.BaseSite>` an error is raised.
"""
if not isinstance(self.parent, blue.SiteType) and not self._IGNORE_CHECKS:
raise ValueError(f'To set the refsite reference, site must be set first.')
if self.refsite is not None:
self.refsite.detach(self)
if refsite is not None:
refsite._ref_actuators.append(self)
self._refsite = refsite
# MUJOCO PROPERTIES
@property
def tag(self) -> str:
"""
The tag will later become the tag name of the xml element.
Returns
-------
str
"""
if self._tag is None:
return self.__class__.__name__.lower()
else:
return self._tag
@tag.setter
@blue.restrict
def tag(self, tag: str|None) -> None:
"""
The tag will later become the tag name of the xml element.
Parameters
----------
tag : str | None
"""
self._tag = tag
@property
def ctrllimited(self) -> bool|None:
"""
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
Returns
-------
bool | None
"""
return self._ctrllimited
@ctrllimited.setter
@blue.restrict
def ctrllimited(self, ctrllimited: bool|None) -> None:
"""
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
Parameters
----------
ctrllimited : bool | None
"""
self._ctrllimited = ctrllimited
@property
def forcelimited(self) -> bool|None:
"""
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
Returns
-------
bool | None
"""
return self._forcelimited
@forcelimited.setter
@blue.restrict
def forcelimited(self, forcelimited: bool|None) -> None:
"""
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
Parameters
----------
forcelimited : bool | None
"""
self._forcelimited = forcelimited
@property
def actlimited(self) -> bool|None:
"""
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
Returns
-------
bool | None
"""
return self._actlimited
@actlimited.setter
@blue.restrict
def actlimited(self, actlimited: bool|None) -> None:
"""
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
Parameters
----------
actlimited : bool | None
"""
self._actlimited = actlimited
@property
def ctrlrange(self) -> np.ndarray:
"""
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
Returns
-------
np.ndarray
"""
return self._ctrlrange
@ctrlrange.setter
@blue.restrict
def ctrlrange(self, ctrlrange: np.ndarray|list[int|float]) -> None:
"""
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
Parameters
----------
ctrlrange : np.ndarray | list[int | float]
"""
self._ctrlrange = np.array(ctrlrange, dtype=np.float32)
@property
def forcerange(self) -> np.ndarray:
"""
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
Returns
-------
np.ndarray
"""
return self._forcerange
@forcerange.setter
@blue.restrict
def forcerange(self, forcerange: np.ndarray|list[int|float]) -> None:
"""
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
Parameters
----------
forcerange : np.ndarray | list[int | float]
"""
self._forcerange = np.array(forcerange, dtype=np.float32)
@property
def actrange(self) -> np.ndarray:
"""
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
Returns
-------
np.ndarray
"""
return self._actrange
@actrange.setter
@blue.restrict
def actrange(self, actrange: np.ndarray|list[int|float]) -> None:
"""
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
Parameters
----------
actrange : np.ndarray | list[int | float]
"""
self._actrange = np.array(actrange, dtype=np.float32)
@property
def lengthrange(self) -> np.ndarray:
"""
Range of feasible lengths of the actuator’s transmission.
Returns
-------
np.ndarray
"""
return self._lengthrange
@lengthrange.setter
@blue.restrict
def lengthrange(self, lengthrange: np.ndarray|list[int|float]) -> None:
"""
Range of feasible lengths of the actuator’s transmission.
Parameters
----------
lengthrange : np.ndarray | list[int | float]
"""
self._lengthrange = np.array(lengthrange, dtype=np.float32)
@property
def gear(self) -> np.ndarray:
"""
This attribute scales the length (and consequently moment arms, velocity and force) of the
Actuator, for all transmission types. It is different from the gain in the force generation
mechanism, because the gain only scales the force output and does not affect the length,
moment arms and velocity. For actuators with scalar transmission, only the first element of
this vector is used. The remaining elements are needed for joint (with or without inparent)
and site transmissions where this attribute is used to specify 3D force and torque axes.
Returns
-------
np.ndarray
"""
return self._gear
@gear.setter
@blue.restrict
def gear(self, gear: np.ndarray|list[int|float]) -> None:
"""
This attribute scales the length (and consequently moment arms, velocity and force) of the
Actuator, for all transmission types. It is different from the gain in the force generation
mechanism, because the gain only scales the force output and does not affect the length,
moment arms and velocity. For actuators with scalar transmission, only the first element of
this vector is used. The remaining elements are needed for joint (with or without inparent)
and site transmissions where this attribute is used to specify 3D force and torque axes.
Parameters
----------
gear : np.ndarray | list[int | float]
"""
self._gear = np.array(gear, dtype=np.float32)
@property
def cranklength(self) -> float:
"""
Used only for the slider-crank transmission type. Specifies the length of the connecting rod.
The compiler expects this value to be positive when a slider-crank transmission is present.
Returns
-------
float
"""
return self._cranklength
@cranklength.setter
@blue.restrict
def cranklength(self, cranklength: int|float) -> None:
"""
Used only for the slider-crank transmission type. Specifies the length of the connecting rod.
The compiler expects this value to be positive when a slider-crank transmission is present.
Parameters
----------
cranklength : int | float
"""
self._cranklength = float(cranklength)
@property
def dyntype(self) -> str:
"""
Activation dynamics type for the actuator. See :attr:`dyntype` for a detailed description.
Returns
-------
str
"""
return self._dyntype
@dyntype.setter
@blue.restrict
def dyntype(self, dyntype: str) -> None:
"""
Activation dynamics type for the actuator. See :attr:`dyntype` for a detailed description.
Parameters
----------
dyntype : str
Legal values are ``'none'``, ``'integrator'``, ``'filter'``, ``'filterexact'``,
``'muscle'`` and ``'user'``.
"""
self._dyntype = dyntype
@property
def gaintype(self) -> str:
"""
The gain and bias together determine the output of the force generation mechanism, which is
currently assumed to be affine. See :attr:`gaintype` for a detailed description.
Returns
-------
str
"""
return self._gaintype
@gaintype.setter
@blue.restrict
def gaintype(self, gaintype: str) -> None:
"""
The gain and bias together determine the output of the force generation mechanism, which is
currently assumed to be affine. See :attr:`gaintype` for a detailed description.
Parameters
----------
gaintype : str
Legal values are ``'fixed'``, ``'affine'``, ``'muscle'`` and ``'user'``.
"""
self._gaintype = gaintype
@property
def biastype(self) -> str:
"""
See :attr:`biastype` for a detailed description.
Returns
-------
str
"""
return self._biastype
@biastype.setter
@blue.restrict
def biastype(self, biastype: str) -> None:
"""
See :attr:`biastype` for a detailed description.
Parameters
----------
biastype : str
Legal values are ``'fixed'``, ``'affine'``, ``'muscle'`` and ``'user'``.
"""
self._biastype = biastype
@property
def dynprm(self) -> np.ndarray:
"""
Activation dynamics parameters. The built-in activation types (except for muscle) use only
the first parameter, but we provide additional parameters in case user callbacks implement
a more elaborate model. The length of this array is not enforced by the parser, so the user
can enter as many parameters as needed. These defaults are not compatible with muscle
actuators.
Returns
-------
np.ndarray
"""
return self._dynprm
@dynprm.setter
@blue.restrict
def dynprm(self, dynprm: int|float|list[int|float]|np.ndarray) -> None:
"""
Activation dynamics parameters. The built-in activation types (except for muscle) use only
the first parameter, but we provide additional parameters in case user callbacks implement
a more elaborate model. The length of this array is not enforced by the parser, so the user
can enter as many parameters as needed. These defaults are not compatible with muscle
actuators.
Parameters
----------
dynprm : int | float | list[int | float] | np.ndarray
"""
if isinstance(dynprm, (int, float)):
dynprm = [dynprm]
self._dynprm = np.array(dynprm, dtype=np.float32)
@property
def gainprm(self) -> np.ndarray:
"""
Gain parameters. The built-in gain types (except for muscle) use only the first parameter,
but we provide additional parameters in case user callbacks implement a more elaborate model.
The length of this array is not enforced by the parser, so the user can enter as many
parameters as needed. These defaults are not compatible with muscle actuators.
Returns
-------
np.ndarray
"""
return self._gainprm
@gainprm.setter
@blue.restrict
def gainprm(self, gainprm: int|float|list[int|float]|np.ndarray) -> None:
"""
Gain parameters. The built-in gain types (except for muscle) use only the first parameter,
but we provide additional parameters in case user callbacks implement a more elaborate model.
The length of this array is not enforced by the parser, so the user can enter as many
parameters as needed. These defaults are not compatible with muscle actuators.
Parameters
----------
gainprm : int | float | list[int | float] | np.ndarray
"""
if isinstance(gainprm, (int, float)):
gainprm = [gainprm]
self._gainprm = np.array(gainprm, dtype=np.float32)
@property
def biasprm(self) -> np.ndarray:
"""
Bias parameters. The affine bias type uses three parameters. The length of this array is not
enforced by the parser, so the user can enter as many parameters as needed. These defaults are
not compatible with muscle actuators.
Returns
-------
np.ndarray
"""
return self._biasprm
@biasprm.setter
@blue.restrict
def biasprm(self, biasprm: int|float|list[int|float]|np.ndarray) -> None:
"""
Bias parameters. The affine bias type uses three parameters. The length of this array is not
enforced by the parser, so the user can enter as many parameters as needed. These defaults are
not compatible with muscle actuators.
Parameters
----------
biasprm : int | float | list[int | float] | np.ndarray
"""
if isinstance(biasprm, (int, float)):
biasprm = [biasprm]
self._biasprm = np.array(biasprm, dtype=np.float32)
[docs]
class General(BaseActuator):
"""
This is the General form of an :class:`Actuator <BaseActuator>`. Useful shortcuts are defined in the
following classes.
Parameters
----------
name : str | None, optional
The user specified name for the Actuator. In the case of a naming conflict the name will be altered
by an enumeration scheme.
inparent : bool, optional
If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
ctrllimited : bool | None, optional
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
forcelimited : bool | None, optional
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
actlimited : bool | None, optional
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
ctrlrange : np.ndarray | list[int | float], optional
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
forcerange : np.ndarray | list[int | float], optional
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
actrange : np.ndarray | list[int | float], optional
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
lengthrange : np.ndarray | list[int | float], optional
Range of feasible lengths of the actuator’s transmission.
gear : np.ndarray | list[int | float], optional
This attribute scales the length (and consequently moment arms, velocity and force) of
the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
detailed description.
cranklength : int | float, optional
Used only for the slider-crank transmission type. Specifies the length of the connecting
rod. The compiler expects this value to be positive when a slider-crank transmission is
present.
dyntype : str, optional
See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
gaintype : str, optional
See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
biastype : str, optional
See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
dynprm : int | float | list[int | float] | np.ndarray, optional
Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
gainprm : int | float | list[int | float] | np.ndarray, optional
The gain and bias together determine the output of the force generation mechanism. See
:attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
biasprm : int | float | list[int | float] | np.ndarray, optional
Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
sensors : list | blue.SensorType | None, optional
The Sensors are attached to the actuator on initialization.
copy : bool, optional
If True, the Sensors passed during init will be copied before attachment, otherwise the original
Sensor is attached.
**kwargs
Keyword arguments are passed to ``super().__init__``.
"""
pass
#class Translation(BaseActuator):
#
# @blue.restrict
# def __init__(self,
# name: str|None = None,
# axis: str|np.ndarray|list[int|float]|None = None,
# ctrllimited: bool|None = None,
# forcelimited: bool|None = None,
# actlimited: bool|None = None,
# ctrlrange: np.ndarray|list[int|float] = [0., 0.],
# forcerange: np.ndarray|list[int|float] = [0., 0.],
# actrange: np.ndarray|list[int|float] = [0., 0.],
# lengthrange: np.ndarray|list[int|float] = [0., 0.],
# cranklength: int|float = 0.,
# dyntype: str = 'none',
# gaintype: str = 'fixed',
# biastype: str = 'none',
# dynprm: int|float|list[int|float]|np.ndarray = 1.,
# gainprm: int|float|list[int|float]|np.ndarray = 1.,
# biasprm: int|float|list[int|float]|np.ndarray = 1.,
# sensors: list|blue.SensorType|None = None,
# copy: bool = True,
# **kwargs):
# """
# Parameters
# ----------
# name : str | None, optional
# The user specified name for the Actuator. In the case of a naming conflict the name will be altered
# by an enumeration scheme.
# inparent : bool, optional
# If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
# the actuator assumes the frame of reference from the parent.
# ctrllimited : bool | None, optional
# If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
# at runtime. If false, control input clamping is disabled.
# forcelimited : bool | None, optional
# If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
# at runtime. If false, force clamping is disabled.
# actlimited : bool | None, optional
# If true, the internal state (activation) associated with this actuator is automatically
# clamped to :attr:`actrange` at runtime.
# ctrlrange : np.ndarray | list[int | float], optional
# Range for clamping the control input. The compiler expects the first value to be smaller
# than the second value.
# forcerange : np.ndarray | list[int | float], optional
# Range for clamping the force output. The compiler expects the first value to be no greater
# than the second value.
# actrange : np.ndarray | list[int | float], optional
# Range for clamping the activation state. The compiler expects the first value to be no
# greater than the second value.
# lengthrange : np.ndarray | list[int | float], optional
# Range of feasible lengths of the actuator’s transmission.
# gear : np.ndarray | list[int | float], optional
# This attribute scales the length (and consequently moment arms, velocity and force) of
# the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
# detailed description.
# cranklength : int | float, optional
# Used only for the slider-crank transmission type. Specifies the length of the connecting
# rod. The compiler expects this value to be positive when a slider-crank transmission is
# present.
# dyntype : str, optional
# See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
# gaintype : str, optional
# See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
# biastype : str, optional
# See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
# dynprm : int | float | list[int | float] | np.ndarray, optional
# Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
# gainprm : int | float | list[int | float] | np.ndarray, optional
# The gain and bias together determine the output of the force generation mechanism. See
# :attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
# biasprm : int | float | list[int | float] | np.ndarray, optional
# Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
# sensors : list | blue.SensorType | None, optional
# The Sensors are attached to the actuator on initialization.
# copy : bool, optional
# If True, the Sensors passed during init will be copied before attachment, otherwise the original
# Sensor is attached.
# **kwargs
# Keyword arguments are passed to ``super().__init__``.
# """
# raise NotImplemented
# if axis is not None:
# if 'gear' in kwargs:
# kwargs.pop('gear')
# axis = blue.utils.geometry.Vector.get_axis(axis)
# gear = np.concatenate([axis, np.zeros(3, dtype=np.float32)])
# else:
# if 'gear' in kwargs:
# gear = kwargs.pop('gear')
# else:
# gear = self._DEFAULT_VALS['gear']
# super().__init__(name=name,
# ctrllimited=ctrllimited,
# forcelimited=forcelimited,
# actlimited=actlimited,
# ctrlrange=ctrlrange,
# forcerange=forcerange,
# actrange=actrange,
# lengthrange=lengthrange,
# gear=gear,
# cranklength=cranklength,
# dyntype=dyntype,
# gaintype=gaintype,
# biastype=biastype,
# dynprm=dynprm,
# gainprm=gainprm,
# biasprm=biasprm,
# sensors=sensors,
# copy=copy,
# **kwargs)
# self.tag = 'general'
#class Rotation(BaseActuator):
#
# @blue.restrict
# def __init__(self,
# name: str|None = None,
# axis: str|np.ndarray|list[int|float]|None = None,
# ctrllimited: bool|None = True,
# forcelimited: bool|None = None,
# actlimited: bool|None = None,
# ctrlrange: np.ndarray|list[int|float] = [-1.571, 1.571],
# forcerange: np.ndarray|list[int|float] = [0., 0.],
# actrange: np.ndarray|list[int|float] = [0., 0.],
# lengthrange: np.ndarray|list[int|float] = [0., 0.],
# cranklength: int|float = 0.,
# dyntype: str = 'none',
# gaintype: str = 'fixed',
# biastype: str = 'none',
# dynprm: int|float|list[int|float]|np.ndarray = 1.,
# gainprm: int|float|list[int|float]|np.ndarray = 1.,
# biasprm: int|float|list[int|float]|np.ndarray = 1.,
# sensors: list|blue.SensorType|None = None,
# copy: bool = True,
# **kwargs):
# """
# Parameters
# ----------
# name : str | None, optional
# The user specified name for the Actuator. In the case of a naming conflict the name will be altered
# by an enumeration scheme.
# inparent : bool, optional
# If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
# the actuator assumes the frame of reference from the parent.
# ctrllimited : bool | None, optional
# If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
# at runtime. If false, control input clamping is disabled.
# forcelimited : bool | None, optional
# If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
# at runtime. If false, force clamping is disabled.
# actlimited : bool | None, optional
# If true, the internal state (activation) associated with this actuator is automatically
# clamped to :attr:`actrange` at runtime.
# ctrlrange : np.ndarray | list[int | float], optional
# Range for clamping the control input. The compiler expects the first value to be smaller
# than the second value.
# forcerange : np.ndarray | list[int | float], optional
# Range for clamping the force output. The compiler expects the first value to be no greater
# than the second value.
# actrange : np.ndarray | list[int | float], optional
# Range for clamping the activation state. The compiler expects the first value to be no
# greater than the second value.
# lengthrange : np.ndarray | list[int | float], optional
# Range of feasible lengths of the actuator’s transmission.
# gear : np.ndarray | list[int | float], optional
# This attribute scales the length (and consequently moment arms, velocity and force) of
# the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
# detailed description.
# cranklength : int | float, optional
# Used only for the slider-crank transmission type. Specifies the length of the connecting
# rod. The compiler expects this value to be positive when a slider-crank transmission is
# present.
# dyntype : str, optional
# See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
# gaintype : str, optional
# See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
# biastype : str, optional
# See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
# dynprm : int | float | list[int | float] | np.ndarray, optional
# Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
# gainprm : int | float | list[int | float] | np.ndarray, optional
# The gain and bias together determine the output of the force generation mechanism. See
# :attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
# biasprm : int | float | list[int | float] | np.ndarray, optional
# Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
# sensors : list | blue.SensorType | None, optional
# The Sensors are attached to the actuator on initialization.
# copy : bool, optional
# If True, the Sensors passed during init will be copied before attachment, otherwise the original
# Sensor is attached.
# **kwargs
# Keyword arguments are passed to ``super().__init__``.
# """
# raise NotImplemented
# if axis is not None:
# if 'gear' in kwargs:
# kwargs.pop('gear')
# axis = blue.utils.geometry.Vector.get_axis(axis)
# gear = np.concatenate([np.zeros(3, dtype=np.float32), axis])
# else:
# if 'gear' in kwargs:
# gear = kwargs.pop('gear')
# else:
# gear = self._DEFAULT_VALS['gear']
# super().__init__(name=name,
# ctrllimited=ctrllimited,
# forcelimited=forcelimited,
# actlimited=actlimited,
# ctrlrange=ctrlrange,
# forcerange=forcerange,
# actrange=actrange,
# lengthrange=lengthrange,
# gear=gear,
# cranklength=cranklength,
# dyntype=dyntype,
# gaintype=gaintype,
# biastype=biastype,
# dynprm=dynprm,
# gainprm=gainprm,
# biasprm=biasprm,
# sensors=sensors,
# copy=copy,
# **kwargs)
# self.tag = 'general'
# ACTUATOR SHORTCUTS
[docs]
class Motor(BaseActuator):
"""
Parameters
----------
name : str | None, optional
The user specified name for the Actuator. In the case of a naming conflict the name will be altered
by an enumeration scheme.
inparent : bool, optional
If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
ctrllimited : bool | None, optional
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
forcelimited : bool | None, optional
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
actlimited : bool | None, optional
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
ctrlrange : np.ndarray | list[int | float], optional
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
forcerange : np.ndarray | list[int | float], optional
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
actrange : np.ndarray | list[int | float], optional
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
lengthrange : np.ndarray | list[int | float], optional
Range of feasible lengths of the actuator’s transmission.
gear : np.ndarray | list[int | float], optional
This attribute scales the length (and consequently moment arms, velocity and force) of
the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
detailed description.
cranklength : int | float, optional
Used only for the slider-crank transmission type. Specifies the length of the connecting
rod. The compiler expects this value to be positive when a slider-crank transmission is
present.
dyntype : str, optional
See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
gaintype : str, optional
See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
biastype : str, optional
See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
dynprm : int | float | list[int | float] | np.ndarray, optional
Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
gainprm : int | float | list[int | float] | np.ndarray, optional
The gain and bias together determine the output of the force generation mechanism. See
:attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
biasprm : int | float | list[int | float] | np.ndarray, optional
Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
sensors : list | blue.SensorType | None, optional
The Sensors are attached to the actuator on initialization.
copy : bool, optional
If True, the Sensors passed during init will be copied before attachment, otherwise the original
Sensor is attached.
**kwargs
Keyword arguments are passed to ``super().__init__``.
"""
pass
[docs]
class Position(BaseActuator):
[docs]
@blue.restrict
def __init__(self,
name: str|None = None,
gear: np.ndarray|list[int|float] = [1., 0., 0., 0., 0., 0.],
kp: int|float = 1.,
ctrllimited: bool|None = True,
forcelimited: bool|None = None,
actlimited: bool|None = None,
ctrlrange: np.ndarray|list[int|float] = [0., 0.],
forcerange: np.ndarray|list[int|float] = [0., 0.],
actrange: np.ndarray|list[int|float] = [0., 0.],
lengthrange: np.ndarray|list[int|float] = [0., 0.],
cranklength: int|float = 0.,
dyntype: str = 'none',
gaintype: str = 'fixed',
biastype: str = 'none',
dynprm: int|float|list[int|float]|np.ndarray = 1.,
gainprm: int|float|list[int|float]|np.ndarray = 1.,
biasprm: int|float|list[int|float]|np.ndarray = 1.,
sensors: list|blue.SensorType|None = None,
copy: bool = True,
**kwargs):
"""
Parameters
----------
name : str | None, optional
The user specified name for the Actuator. In the case of a naming conflict the name will be altered
by an enumeration scheme.
kp : int|float
Position feedback gain.
inparent : bool, optional
If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
ctrllimited : bool | None, optional
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
forcelimited : bool | None, optional
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
actlimited : bool | None, optional
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
ctrlrange : np.ndarray | list[int | float], optional
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
forcerange : np.ndarray | list[int | float], optional
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
actrange : np.ndarray | list[int | float], optional
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
lengthrange : np.ndarray | list[int | float], optional
Range of feasible lengths of the actuator’s transmission.
gear : np.ndarray | list[int | float], optional
This attribute scales the length (and consequently moment arms, velocity and force) of
the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
detailed description.
cranklength : int | float, optional
Used only for the slider-crank transmission type. Specifies the length of the connecting
rod. The compiler expects this value to be positive when a slider-crank transmission is
present.
dyntype : str, optional
See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
gaintype : str, optional
See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
biastype : str, optional
See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
dynprm : int | float | list[int | float] | np.ndarray, optional
Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
gainprm : int | float | list[int | float] | np.ndarray, optional
The gain and bias together determine the output of the force generation mechanism. See
:attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
biasprm : int | float | list[int | float] | np.ndarray, optional
Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
sensors : list | blue.SensorType | None, optional
The Sensors are attached to the actuator on initialization.
copy : bool, optional
If True, the Sensors passed during init will be copied before attachment, otherwise the original
Sensor is attached.
**kwargs
Keyword arguments are passed to ``super().__init__``.
"""
self.kp = kp
super().__init__(name=name,
ctrllimited=ctrllimited,
forcelimited=forcelimited,
actlimited=actlimited,
ctrlrange=ctrlrange,
forcerange=forcerange,
actrange=actrange,
lengthrange=lengthrange,
gear=gear,
cranklength=cranklength,
dyntype=dyntype,
gaintype=gaintype,
biastype=biastype,
dynprm=dynprm,
gainprm=gainprm,
biasprm=biasprm,
sensors=sensors,
copy=copy,
**kwargs)
@property
def kp(self) -> float:
"""
Position feedback gain.
Returns
-------
float
"""
return self._kp
@kp.setter
@blue.restrict
def kp(self, kp: int|float) -> None:
"""
Parameters
----------
kp : int | float
Position feedback gain.
"""
self._kp = float(kp)
[docs]
class Velocity(BaseActuator):
[docs]
@blue.restrict
def __init__(self,
name: str|None = None,
gear: np.ndarray|list[int|float] = [1., 0., 0., 0., 0., 0.],
kv: int|float = 1.,
ctrllimited: bool|None = True,
forcelimited: bool|None = None,
actlimited: bool|None = None,
ctrlrange: np.ndarray|list[int|float] = [0., 0.],
forcerange: np.ndarray|list[int|float] = [0., 0.],
actrange: np.ndarray|list[int|float] = [0., 0.],
lengthrange: np.ndarray|list[int|float] = [0., 0.],
cranklength: int|float = 0.,
dyntype: str = 'none',
gaintype: str = 'fixed',
biastype: str = 'none',
dynprm: int|float|list[int|float]|np.ndarray = 1.,
gainprm: int|float|list[int|float]|np.ndarray = 1.,
biasprm: int|float|list[int|float]|np.ndarray = 1.,
sensors: list|blue.SensorType|None = None,
copy: bool = True,
**kwargs):
"""
Parameters
----------
name : str | None, optional
The user specified name for the Actuator. In the case of a naming conflict the name will be altered
by an enumeration scheme.
kv : int|float
Velocity feedback gain.
inparent : bool, optional
If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
ctrllimited : bool | None, optional
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
forcelimited : bool | None, optional
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
actlimited : bool | None, optional
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
ctrlrange : np.ndarray | list[int | float], optional
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
forcerange : np.ndarray | list[int | float], optional
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
actrange : np.ndarray | list[int | float], optional
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
lengthrange : np.ndarray | list[int | float], optional
Range of feasible lengths of the actuator’s transmission.
gear : np.ndarray | list[int | float], optional
This attribute scales the length (and consequently moment arms, velocity and force) of
the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
detailed description.
cranklength : int | float, optional
Used only for the slider-crank transmission type. Specifies the length of the connecting
rod. The compiler expects this value to be positive when a slider-crank transmission is
present.
dyntype : str, optional
See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
gaintype : str, optional
See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
biastype : str, optional
See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
dynprm : int | float | list[int | float] | np.ndarray, optional
Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
gainprm : int | float | list[int | float] | np.ndarray, optional
The gain and bias together determine the output of the force generation mechanism. See
:attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
biasprm : int | float | list[int | float] | np.ndarray, optional
Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
sensors : list | blue.SensorType | None, optional
The Sensors are attached to the actuator on initialization.
copy : bool, optional
If True, the Sensors passed during init will be copied before attachment, otherwise the original
Sensor is attached.
**kwargs
Keyword arguments are passed to ``super().__init__``.
"""
self.kv = kv
super().__init__(name=name,
ctrllimited=ctrllimited,
forcelimited=forcelimited,
actlimited=actlimited,
ctrlrange=ctrlrange,
forcerange=forcerange,
actrange=actrange,
lengthrange=lengthrange,
gear=gear,
cranklength=cranklength,
dyntype=dyntype,
gaintype=gaintype,
biastype=biastype,
dynprm=dynprm,
gainprm=gainprm,
biasprm=biasprm,
sensors=sensors,
copy=copy,
**kwargs)
@property
def kv(self) -> float:
"""
Velocity feedback gain.
Returns
-------
float
"""
return self._kv
@kv.setter
@blue.restrict
def kv(self, kv: int|float) -> None:
"""
Parameters
----------
kv : int | float
Velocity feedback gain.
"""
self._kv = float(kv)
[docs]
class IntVelocity(BaseActuator):
[docs]
@blue.restrict
def __init__(self,
name: str|None = None,
gear: np.ndarray|list[int|float] = [1., 0., 0., 0., 0., 0.],
kp: int|float = 1.,
ctrllimited: bool|None = True,
forcelimited: bool|None = None,
actlimited: bool|None = None,
ctrlrange: np.ndarray|list[int|float] = [0., 0.],
forcerange: np.ndarray|list[int|float] = [0., 0.],
actrange: np.ndarray|list[int|float] = [0., 0.],
lengthrange: np.ndarray|list[int|float] = [0., 0.],
cranklength: int|float = 0.,
dyntype: str = 'none',
gaintype: str = 'fixed',
biastype: str = 'none',
dynprm: int|float|list[int|float]|np.ndarray = 1.,
gainprm: int|float|list[int|float]|np.ndarray = 1.,
biasprm: int|float|list[int|float]|np.ndarray = 1.,
sensors: list|blue.SensorType|None = None,
copy: bool = True,
**kwargs):
"""
Parameters
----------
name : str | None, optional
The user specified name for the Actuator. In the case of a naming conflict the name will be altered
by an enumeration scheme.
kp : int | float
Position feedback gain.
inparent : bool, optional
If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
ctrllimited : bool | None, optional
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
forcelimited : bool | None, optional
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
actlimited : bool | None, optional
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
ctrlrange : np.ndarray | list[int | float], optional
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
forcerange : np.ndarray | list[int | float], optional
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
actrange : np.ndarray | list[int | float], optional
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
lengthrange : np.ndarray | list[int | float], optional
Range of feasible lengths of the actuator’s transmission.
gear : np.ndarray | list[int | float], optional
This attribute scales the length (and consequently moment arms, velocity and force) of
the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
detailed description.
cranklength : int | float, optional
Used only for the slider-crank transmission type. Specifies the length of the connecting
rod. The compiler expects this value to be positive when a slider-crank transmission is
present.
dyntype : str, optional
See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
gaintype : str, optional
See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
biastype : str, optional
See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
dynprm : int | float | list[int | float] | np.ndarray, optional
Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
gainprm : int | float | list[int | float] | np.ndarray, optional
The gain and bias together determine the output of the force generation mechanism. See
:attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
biasprm : int | float | list[int | float] | np.ndarray, optional
Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
sensors : list | blue.SensorType | None, optional
The Sensors are attached to the actuator on initialization.
copy : bool, optional
If True, the Sensors passed during init will be copied before attachment, otherwise the original
Sensor is attached.
**kwargs
Keyword arguments are passed to ``super().__init__``.
"""
self.kp = kp
super().__init__(name=name,
ctrllimited=ctrllimited,
forcelimited=forcelimited,
actlimited=actlimited,
ctrlrange=ctrlrange,
forcerange=forcerange,
actrange=actrange,
lengthrange=lengthrange,
gear=gear,
cranklength=cranklength,
dyntype=dyntype,
gaintype=gaintype,
biastype=biastype,
dynprm=dynprm,
gainprm=gainprm,
biasprm=biasprm,
sensors=sensors,
copy=copy,
**kwargs)
@property
def kp(self) -> float:
"""
Position feedback gain.
Returns
-------
float
"""
return self._kp
@kp.setter
@blue.restrict
def kp(self, kp: int|float) -> None:
"""
Parameters
----------
kp : int | float
Position feedback gain.
"""
self._kp = float(kp)
[docs]
class Damper(BaseActuator):
[docs]
@blue.restrict
def __init__(self,
name: str|None = None,
gear: np.ndarray|list[int|float] = [1., 0., 0., 0., 0., 0.],
kv: int|float = 1.,
ctrllimited: bool|None = True,
forcelimited: bool|None = None,
actlimited: bool|None = None,
ctrlrange: np.ndarray|list[int|float] = [0., 0.],
forcerange: np.ndarray|list[int|float] = [0., 0.],
actrange: np.ndarray|list[int|float] = [0., 0.],
lengthrange: np.ndarray|list[int|float] = [0., 0.],
cranklength: int|float = 0.,
dyntype: str = 'none',
gaintype: str = 'fixed',
biastype: str = 'none',
dynprm: int|float|list[int|float]|np.ndarray = 1.,
gainprm: int|float|list[int|float]|np.ndarray = 1.,
biasprm: int|float|list[int|float]|np.ndarray = 1.,
sensors: list|blue.SensorType|None = None,
copy: bool = True,
**kwargs):
"""
Parameters
----------
name : str | None, optional
The user specified name for the Actuator. In the case of a naming conflict the name will be altered
by an enumeration scheme.
kv : int | float
Velocity feedback gain.
inparent : bool, optional
If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
ctrllimited : bool | None, optional
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
forcelimited : bool | None, optional
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
actlimited : bool | None, optional
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
ctrlrange : np.ndarray | list[int | float], optional
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
forcerange : np.ndarray | list[int | float], optional
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
actrange : np.ndarray | list[int | float], optional
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
lengthrange : np.ndarray | list[int | float], optional
Range of feasible lengths of the actuator’s transmission.
gear : np.ndarray | list[int | float], optional
This attribute scales the length (and consequently moment arms, velocity and force) of
the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
detailed description.
cranklength : int | float, optional
Used only for the slider-crank transmission type. Specifies the length of the connecting
rod. The compiler expects this value to be positive when a slider-crank transmission is
present.
dyntype : str, optional
See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
gaintype : str, optional
See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
biastype : str, optional
See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
dynprm : int | float | list[int | float] | np.ndarray, optional
Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
gainprm : int | float | list[int | float] | np.ndarray, optional
The gain and bias together determine the output of the force generation mechanism. See
:attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
biasprm : int | float | list[int | float] | np.ndarray, optional
Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
sensors : list | blue.SensorType | None, optional
The Sensors are attached to the actuator on initialization.
copy : bool, optional
If True, the Sensors passed during init will be copied before attachment, otherwise the original
Sensor is attached.
**kwargs
Keyword arguments are passed to ``super().__init__``.
"""
self.kv = kv
super().__init__(name=name,
ctrllimited=ctrllimited,
forcelimited=forcelimited,
actlimited=actlimited,
ctrlrange=ctrlrange,
forcerange=forcerange,
actrange=actrange,
lengthrange=lengthrange,
gear=gear,
cranklength=cranklength,
dyntype=dyntype,
gaintype=gaintype,
biastype=biastype,
dynprm=dynprm,
gainprm=gainprm,
biasprm=biasprm,
sensors=sensors,
copy=copy,
**kwargs)
@property
def kv(self) -> float:
"""
Velocity feedback gain.
Returns
-------
float
"""
return self._kv
@kv.setter
@blue.restrict
def kv(self, kv: int|float) -> None:
"""
Parameters
----------
kv : int | float
Velocity feedback gain.
"""
self._kv = float(kv)
[docs]
class Cylinder(BaseActuator):
[docs]
@blue.restrict
def __init__(self,
name: str|None = None,
gear: np.ndarray|list[int|float] = [1., 0., 0., 0., 0., 0.],
timeconst: int|float = 1.,
area: int|float = 1.,
diameter: int|float|None = None,
bias: np.ndarray|list[int|float] = [0., 0., 0.],
ctrllimited: bool|None = True,
forcelimited: bool|None = None,
actlimited: bool|None = None,
ctrlrange: np.ndarray|list[int|float] = [0., 0.],
forcerange: np.ndarray|list[int|float] = [0., 0.],
actrange: np.ndarray|list[int|float] = [0., 0.],
lengthrange: np.ndarray|list[int|float] = [0., 0.],
cranklength: int|float = 0.,
dyntype: str = 'none',
gaintype: str = 'fixed',
biastype: str = 'none',
dynprm: int|float|list[int|float]|np.ndarray = 1.,
gainprm: int|float|list[int|float]|np.ndarray = 1.,
biasprm: int|float|list[int|float]|np.ndarray = 1.,
sensors: list|blue.SensorType|None = None,
copy: bool = True,
**kwargs):
"""
Parameters
----------
name : str | None, optional
The user specified name for the Actuator. In the case of a naming conflict the name will be altered
by an enumeration scheme.
timeconst : int | float
Time constant of the activation dynamics.
area : int | float
Area of the cylinder. This is used internally as actuator gain.
diameter : int | float | None
Instead of area the user can specify diameter. If both are specified, diameter has precedence.
bias : np.ndarray | list[int | float]
Bias parameters, copied internally into biasprm.
inparent : bool, optional
If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
ctrllimited : bool | None, optional
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
forcelimited : bool | None, optional
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
actlimited : bool | None, optional
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
ctrlrange : np.ndarray | list[int | float], optional
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
forcerange : np.ndarray | list[int | float], optional
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
actrange : np.ndarray | list[int | float], optional
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
lengthrange : np.ndarray | list[int | float], optional
Range of feasible lengths of the actuator’s transmission.
gear : np.ndarray | list[int | float], optional
This attribute scales the length (and consequently moment arms, velocity and force) of
the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
detailed description.
cranklength : int | float, optional
Used only for the slider-crank transmission type. Specifies the length of the connecting
rod. The compiler expects this value to be positive when a slider-crank transmission is
present.
dyntype : str, optional
See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
gaintype : str, optional
See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
biastype : str, optional
See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
dynprm : int | float | list[int | float] | np.ndarray, optional
Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
gainprm : int | float | list[int | float] | np.ndarray, optional
The gain and bias together determine the output of the force generation mechanism. See
:attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
biasprm : int | float | list[int | float] | np.ndarray, optional
Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
sensors : list | blue.SensorType | None, optional
The Sensors are attached to the actuator on initialization.
copy : bool, optional
If True, the Sensors passed during init will be copied before attachment, otherwise the original
Sensor is attached.
**kwargs
Keyword arguments are passed to ``super().__init__``.
"""
self.timeconst = timeconst
self.area = area
self.diameter = diameter
self.bias = bias
super().__init__(name=name,
ctrllimited=ctrllimited,
forcelimited=forcelimited,
actlimited=actlimited,
ctrlrange=ctrlrange,
forcerange=forcerange,
actrange=actrange,
lengthrange=lengthrange,
gear=gear,
cranklength=cranklength,
dyntype=dyntype,
gaintype=gaintype,
biastype=biastype,
dynprm=dynprm,
gainprm=gainprm,
biasprm=biasprm,
sensors=sensors,
copy=copy,
**kwargs)
@property
def timeconst(self) -> float:
"""
Time constant of the activation dynamics.
Returns
-------
float
"""
return self._timeconst
@timeconst.setter
@blue.restrict
def timeconst(self, timeconst: int|float) -> None:
"""
Parameters
----------
timeconst : int | float
Time constant of the activation dynamics.
"""
self._timeconst = float(timeconst)
@property
def area(self) -> float:
"""
Area of the cylinder. This is used internally as actuator gain.
Returns
-------
float
"""
return self._area
@area.setter
@blue.restrict
def area(self, area: int|float) -> None:
"""
Parameters
----------
area : int | float
Area of the cylinder. This is used internally as actuator gain.
"""
self._area = float(area)
@property
def diameter(self) -> float|None:
"""
Instead of area the user can specify diameter. If both are specified, diameter has precedence.
Returns
-------
float | None
"""
return self._diameter
@diameter.setter
@blue.restrict
def diameter(self, diameter: int|float|None) -> None:
"""
Parameters
----------
diameter : int | float | None
Instead of area the user can specify diameter. If both are specified, diameter has precedence.
"""
self._diameter = None if diameter is None else float(diameter)
@property
def bias(self) -> np.ndarray:
"""
Bias parameters, copied internally into biasprm.
Returns
-------
np.ndarray
"""
return self._bias
@bias.setter
@blue.restrict
def bias(self, bias: list[int|float]|np.ndarray) -> None:
"""
Parameters
----------
bias : list[int | float] | np.ndarray
Bias parameters, copied internally into biasprm.
"""
self._bias = np.array(bias, dtype=np.float32)
[docs]
class Muscle(BaseActuator):
[docs]
@blue.restrict
def __init__(self,
name: str|None = None,
gear: np.ndarray|list[int|float] = [1., 0., 0., 0., 0., 0.],
timeconst: np.ndarray|list[int|float] = [0.01, 0.04],
tausmooth: int|float = 0.,
range: np.ndarray|list[int|float] = [0.75, 1.05],
force: int|float = -1.,
scale: int|float = 200,
lmin: int|float = 0.5,
lmax: int|float = 1.6,
vmax: int|float = 1.5,
fpmax: int|float = 1.3,
fvmax: int|float = 1.2,
ctrllimited: bool|None = True,
forcelimited: bool|None = None,
actlimited: bool|None = None,
ctrlrange: np.ndarray|list[int|float] = [0., 0.],
forcerange: np.ndarray|list[int|float] = [0., 0.],
actrange: np.ndarray|list[int|float] = [0., 0.],
lengthrange: np.ndarray|list[int|float] = [0., 0.],
cranklength: int|float = 0.,
dyntype: str = 'none',
gaintype: str = 'fixed',
biastype: str = 'none',
dynprm: int|float|list[int|float]|np.ndarray = 1.,
gainprm: int|float|list[int|float]|np.ndarray = 1.,
biasprm: int|float|list[int|float]|np.ndarray = 1.,
sensors: list|blue.SensorType|None = None,
copy: bool = True,
**kwargs):
"""
Parameters
----------
name : str | None, optional
The user specified name for the Actuator. In the case of a naming conflict the name will be altered
by an enumeration scheme.
timeconst : np.ndarray | list[int | float]
Time constants for activation and de-activation dynamics.
tausmooth : int | float
Width of smooth transition between activation and deactivation time constants. Units of ctrl,
must be nonegative.
range : np.ndarray | list[int | float]
Operating length range of the muscle, in units of L0.
force : int | float
Peak active force at rest. If this value is negative, the peak force is determined automatically
using the scale attribute below.
scale : int | float
If the force attribute is negative, the peak active force for the muscle is set to this value
divided by mjModel.actuator_acc0. The latter is the norm of the joint-space acceleration vector
caused by unit force on the actuator’s transmission in qpos0. In other words, scaling produces
higher peak forces for muscles that pull more weight.
lmin : int | float
Lower position range of the normalized FLV curve, in units of L0.
lmax : int | float
Upper position range of the normalized FLV curve, in units of L0.
vmax : int | float
Shortening velocity at which muscle force drops to zero, in units of L0 per second.
fpmax : int | float
Passive force generated at lmax, relative to the peak rest force.
fvmax : int | float
Active force generated at saturating lengthening velocity, relative to the peak rest force.
inparent : bool, optional
If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
ctrllimited : bool | None, optional
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
forcelimited : bool | None, optional
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
actlimited : bool | None, optional
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
ctrlrange : np.ndarray | list[int | float], optional
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
forcerange : np.ndarray | list[int | float], optional
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
actrange : np.ndarray | list[int | float], optional
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
lengthrange : np.ndarray | list[int | float], optional
Range of feasible lengths of the actuator’s transmission.
gear : np.ndarray | list[int | float], optional
This attribute scales the length (and consequently moment arms, velocity and force) of
the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
detailed description.
cranklength : int | float, optional
Used only for the slider-crank transmission type. Specifies the length of the connecting
rod. The compiler expects this value to be positive when a slider-crank transmission is
present.
dyntype : str, optional
See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
gaintype : str, optional
See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
biastype : str, optional
See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
dynprm : int | float | list[int | float] | np.ndarray, optional
Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
gainprm : int | float | list[int | float] | np.ndarray, optional
The gain and bias together determine the output of the force generation mechanism. See
:attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
biasprm : int | float | list[int | float] | np.ndarray, optional
Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
sensors : list | blue.SensorType | None, optional
The Sensors are attached to the actuator on initialization.
copy : bool, optional
If True, the Sensors passed during init will be copied before attachment, otherwise the original
Sensor is attached.
**kwargs
Keyword arguments are passed to ``super().__init__``.
"""
self.timeconst = timeconst
self.tausmooth = tausmooth
self.range = range
self.force = force
self.scale = scale
self.lmin = lmin
self.lmax = lmax
self.vmax = vmax
self.fpmax = fpmax
self.fvmax = fvmax
super().__init__(name=name,
ctrllimited=ctrllimited,
forcelimited=forcelimited,
actlimited=actlimited,
ctrlrange=ctrlrange,
forcerange=forcerange,
actrange=actrange,
lengthrange=lengthrange,
gear=gear,
cranklength=cranklength,
dyntype=dyntype,
gaintype=gaintype,
biastype=biastype,
dynprm=dynprm,
gainprm=gainprm,
biasprm=biasprm,
sensors=sensors,
copy=copy,
**kwargs)
@property
def timeconst(self) -> np.ndarray:
"""
Time constants for activation and de-activation dynamics.
Returns
-------
np.ndarray
"""
return self._timeconst
@timeconst.setter
@blue.restrict
def timeconst(self, timeconst: np.ndarray|list[int|float]) -> None:
"""
Parameters
----------
timeconst : np.ndarray | list[int | float]
Time constants for activation and de-activation dynamics.
"""
self._timeconst = np.array(timeconst, dtype=np.float32)
@property
def tausmooth(self) -> float:
"""
Width of smooth transition between activation and deactivation time constants. Units of
ctrl, must be nonegative.
Returns
-------
float
"""
return self._area
@tausmooth.setter
@blue.restrict
def tausmooth(self, tausmooth: int|float) -> None:
"""
Parameters
----------
tausmooth : int | float
Width of smooth transition between activation and deactivation time constants. Units of
ctrl, must be nonegative.
"""
self._tausmooth = float(tausmooth)
@property
def range(self) -> np.ndarray:
"""
Operating length range of the muscle, in units of L0.
Returns
-------
np.ndarray
"""
return self._range
@range.setter
@blue.restrict
def range(self, range: np.ndarray|list[int|float]) -> None:
"""
Parameters
----------
range : np.ndarray | list[int | float]
Operating length range of the muscle, in units of L0.
"""
self._range = np.array(range, dtype=np.float32)
@property
def force(self) -> float:
"""
Peak active force at rest. If this value is negative, the peak force is determined
automatically using the scale attribute below.
Returns
-------
float
"""
return self._force
@force.setter
@blue.restrict
def force(self, force: int|float|np.int32|np.int64|np.float32|np.float64) -> None:
"""
Parameters
----------
force : int | float
Peak active force at rest. If this value is negative, the peak force is determined
automatically using the scale attribute below.
"""
self._force = float(force)
@property
def scale(self) -> float:
"""
If the force attribute is negative, the peak active force for the muscle is set to this value
divided by mjModel.actuator_acc0. The latter is the norm of the joint-space acceleration vector
caused by unit force on the actuator’s transmission in qpos0. In other words, scaling produces
higher peak forces for muscles that pull more weight.
Returns
-------
float
"""
return self._scale
@scale.setter
@blue.restrict
def scale(self, scale: int|float) -> None:
"""
Parameters
----------
scale : int | float
If the force attribute is negative, the peak active force for the muscle is set to this
value divided by mjModel.actuator_acc0. The latter is the norm of the joint-space
acceleration vector caused by unit force on the actuator’s transmission in qpos0. In other
words, scaling produces higher peak forces for muscles that pull more weight.
"""
self._scale = float(scale)
@property
def lmin(self) -> float:
"""
Lower position range of the normalized FLV curve, in units of L0.
Returns
-------
float
"""
return self._lmin
@lmin.setter
@blue.restrict
def lmin(self, lmin: int|float) -> None:
"""
Parameters
----------
lmin : int | float
Lower position range of the normalized FLV curve, in units of L0.
"""
self._lmin = float(lmin)
@property
def lmax(self) -> float:
"""
Upper position range of the normalized FLV curve, in units of L0.
Returns
-------
float
"""
return self._flmax
@lmax.setter
@blue.restrict
def lmax(self, lmax: int|float) -> None:
"""
Parameters
----------
lmax : int | float
Upper position range of the normalized FLV curve, in units of L0.
"""
self._lmax = float(lmax)
@property
def vmax(self) -> float:
"""
Shortening velocity at which muscle force drops to zero, in units of L0 per second.
Returns
-------
float
"""
return self._vmax
@vmax.setter
@blue.restrict
def vmax(self, vmax: int|float) -> None:
"""
Parameters
----------
vmax : int | float
Shortening velocity at which muscle force drops to zero, in units of L0 per second.
"""
self._vmax = float(vmax)
@property
def fpmax(self) -> float:
"""
Passive force generated at lmax, relative to the peak rest force.
Returns
-------
float
"""
return self._fpmax
@fpmax.setter
@blue.restrict
def fpmax(self, fpmax: int|float) -> None:
"""
Parameters
----------
fpmax : int | float
Passive force generated at lmax, relative to the peak rest force.
"""
self._fpmax = float(fpmax)
@property
def fvmax(self) -> float:
"""
Active force generated at saturating lengthening velocity, relative to the peak rest force.
Returns
-------
float
"""
return self._fvmax
@fvmax.setter
@blue.restrict
def fvmax(self, fvmax: int|float) -> None:
"""
Parameters
----------
fvmax : int | float
Active force generated at saturating lengthening velocity, relative to the peak rest force.
"""
self._fvmax = float(fvmax)
[docs]
class Adhesion(BaseActuator):
[docs]
@blue.restrict
def __init__(self,
name: str|None = None,
gear: np.ndarray|list[int|float] = [1., 0., 0., 0., 0., 0.],
gain: int|float = 1.,
ctrllimited: bool|None = None,
forcelimited: bool|None = None,
actlimited: bool|None = None,
ctrlrange: np.ndarray|list[int|float] = [0., 1.],
forcerange: np.ndarray|list[int|float] = [0., 0.],
actrange: np.ndarray|list[int|float] = [0., 0.],
lengthrange: np.ndarray|list[int|float] = [0., 0.],
cranklength: int|float = 0.,
dyntype: str = 'none',
gaintype: str = 'fixed',
biastype: str = 'none',
dynprm: int|float|list[int|float]|np.ndarray = 1.,
gainprm: int|float|list[int|float]|np.ndarray = 1.,
biasprm: int|float|list[int|float]|np.ndarray = 1.,
sensors: list|blue.SensorType|None = None,
copy: bool = True,
**kwargs):
"""
Parameters
----------
name : str | None, optional
The user specified name for the Actuator. In the case of a naming conflict the name will
be altered by an enumeration scheme.
gain : int | float
Gain of the adhesion actuator, in units of force. The total adhesion force applied by the
Actuator is the control value multiplied by the gain. This force is distributed equally
between all the contacts involving geoms belonging to the target Body.
inparent : bool, optional
If `:attr:`inparent` is True and the parent of the Actuator is :class:`Joint <blueprints.joints.BaseJoint>`
the actuator assumes the frame of reference from the parent.
ctrllimited : bool | None, optional
If true, the control input to this actuator is automatically clamped to :attr:`ctrlrange`
at runtime. If false, control input clamping is disabled.
forcelimited : bool | None, optional
If true, the force output of this actuator is automatically clamped to :attr:`forcerange`
at runtime. If false, force clamping is disabled.
actlimited : bool | None, optional
If true, the internal state (activation) associated with this actuator is automatically
clamped to :attr:`actrange` at runtime.
ctrlrange : np.ndarray | list[int | float], optional
Range for clamping the control input. The compiler expects the first value to be smaller
than the second value.
forcerange : np.ndarray | list[int | float], optional
Range for clamping the force output. The compiler expects the first value to be no greater
than the second value.
actrange : np.ndarray | list[int | float], optional
Range for clamping the activation state. The compiler expects the first value to be no
greater than the second value.
lengthrange : np.ndarray | list[int | float], optional
Range of feasible lengths of the actuator’s transmission.
gear : np.ndarray | list[int | float], optional
This attribute scales the length (and consequently moment arms, velocity and force) of
the actuator, for all transmission types. See :attr:`gear <BaseActuator.gear>` for a
detailed description.
cranklength : int | float, optional
Used only for the slider-crank transmission type. Specifies the length of the connecting
rod. The compiler expects this value to be positive when a slider-crank transmission is
present.
dyntype : str, optional
See :attr:`dyntype <BaseActuator.dyntype>` for a detailed description.
gaintype : str, optional
See :attr:`gaintype <BaseActuator.gaintype>` for a detailed description.
biastype : str, optional
See :attr:`biastype <BaseActuator.biastype>` for a detailed description.
dynprm : int | float | list[int | float] | np.ndarray, optional
Activation dynamics parameters. See :attr:`dynprm <BaseActuator.dynprm>` for a detailed description.
gainprm : int | float | list[int | float] | np.ndarray, optional
The gain and bias together determine the output of the force generation mechanism. See
:attr:`gainprm <BaseActuator.gainprm>` for a detailed description.
biasprm : int | float | list[int | float] | np.ndarray, optional
Bias parameters. See :attr:`biasprm <BaseActuator.biasprm>` for a detailed description.
sensors : list | blue.SensorType | None, optional
The Sensors are attached to the actuator on initialization.
copy : bool, optional
If True, the Sensors passed during init will be copied before attachment, otherwise the original
Sensor is attached.
**kwargs
Keyword arguments are passed to ``super().__init__``.
"""
self.gain = gain
super().__init__(name=name,
ctrllimited=ctrllimited,
forcelimited=forcelimited,
actlimited=actlimited,
ctrlrange=ctrlrange,
forcerange=forcerange,
actrange=actrange,
lengthrange=lengthrange,
gear=gear,
cranklength=cranklength,
dyntype=dyntype,
gaintype=gaintype,
biastype=biastype,
dynprm=dynprm,
gainprm=gainprm,
biasprm=biasprm,
sensors=sensors,
copy=copy,
**kwargs)
@property
def parent(self) -> blue.BodyType|None:
"""
The parent to which the Thing is attach, if it unattached parent is None.
Returns
-------
blueBodyType
"""
if hasattr(self, '_parent'):
return self._parent
else:
return None
#return self._parent # super().super().__getattribute__('parent')
@parent.setter
@blue.restrict
def parent(self, parent: blue.BodyType|None) -> None:
"""
Parameters
----------
parent : blueBodyType
The parent to which the Thing is attach, if it unattached parent is None. Only
:class:`Bodies <blueprints.body.Body>` are valid parents of :class:`Adhesion`.
"""
# OLD
#super().__setattr__('parent', parent)
# NEW
if parent is not None and self.parent is not parent and self not in parent:
parent.attach(self, copy=False)
self._parent = parent
@property
def gain(self) -> float:
"""
Gain of the adhesion actuator, in units of force. The total adhesion force applied by the
Actuator is the control value multiplied by the gain. This force is distributed equally
between all the contacts involving geoms belonging to the target Body.
Returns
-------
float
"""
return self._fvmax
@gain.setter
@blue.restrict
def gain(self, gain: int|float) -> None:
"""
Parameters
----------
gain : int | float
Gain of the adhesion actuator, in units of force. The total adhesion force applied by the
Actuator is the control value multiplied by the gain. This force is distributed equally
between all the contacts involving geoms belonging to the target Body.
"""
self._gain = float(gain)
ACTUATOR_THINGS = {'general': General,
'motor': Motor,
'position': Position,
'velocity': Velocity,
'intvelocity': IntVelocity,
'damper': Damper,
'cylinder': Cylinder,
'muscle': Muscle,
'adhesion': Adhesion}