Skip to content

base

base

MLP-based proprioceptive state encoder.

ProprioceptiveEncoder

ProprioceptiveEncoder(input_keys, output_dim, hidden_dimensions=None, activation=value, dropout=0.0, pretrained=False, frozen=False, model_dtype=None)

Bases: Encoder

Encoding proprioceptive state (robot joint positions, velocities, etc.) with a Feedforward Fully-Connected NN.

Initialize proprioceptive encoder.

Parameters:

Name Type Description Default
input_keys str | list[str]

Keys for proprioceptive inputs

required
output_dim int

Output feature dimension

required
hidden_dimensions list[int] | None

Hidden layer dimensions. If None or [], creates simple linear layer. If [128], creates one hidden layer. If [256, 128], creates two hidden layers.

None
activation str

Activation function from ActivationFunction enum

value
dropout float

Dropout rate between layers

0.0
pretrained bool

Whether to use pretrained weights (unused for proprio encoder)

False
frozen bool

Whether to freeze encoder weights

False
model_dtype str | None

Precision string from experiment config (e.g. "bf16-mixed").

None
Source code in src/versatil/models/encoding/encoders/proprioceptive/base.py
def __init__(
    self,
    input_keys: str | list[str],
    output_dim: int,
    hidden_dimensions: list[int] | None = None,
    activation: str = ActivationFunction.RELU.value,
    dropout: float = 0.0,
    pretrained: bool = False,
    frozen: bool = False,
    model_dtype: str | None = None,
):
    """Initialize proprioceptive encoder.

    Args:
        input_keys: Keys for proprioceptive inputs
        output_dim: Output feature dimension
        hidden_dimensions: Hidden layer dimensions. If None or [], creates simple linear layer.
                    If [128], creates one hidden layer. If [256, 128], creates two hidden layers.
        activation: Activation function from ActivationFunction enum
        dropout: Dropout rate between layers
        pretrained: Whether to use pretrained weights (unused for proprio encoder)
        frozen: Whether to freeze encoder weights
        model_dtype: Precision string from experiment config (e.g. ``"bf16-mixed"``).
    """
    specification = EncoderInput(keys=input_keys)
    super().__init__(
        input_specification=specification,
        pretrained=pretrained,
        frozen=frozen,
        model_dtype=model_dtype,
    )
    self.output_dim = output_dim
    self.hidden_dimensions = hidden_dimensions
    self.dropout = dropout
    self.activation_fn = ActivationFunction(activation).to_torch_activation()
    self.network: MLP | None = None

encode

encode(inputs)

Encode proprioceptive state.

Parameters:

Name Type Description Default
inputs dict[str, Tensor]

Dict with state tensors, each as (B, D).

required

Returns:

Type Description
dict[str, Tensor]

Dict with proprioceptive features.

Source code in src/versatil/models/encoding/encoders/proprioceptive/base.py
def encode(self, inputs: dict[str, torch.Tensor]) -> dict[str, torch.Tensor]:
    """Encode proprioceptive state.

    Args:
        inputs: Dict with state tensors, each as (B, D).

    Returns:
        Dict with proprioceptive features.
    """
    state = torch.cat(
        [inputs[key] for key in self.input_specification.keys], dim=-1
    )
    input_dimension = state.shape[-1]
    if self.network is None:
        self._build_network(input_dimension)
        if self.network is None:
            raise RuntimeError("Network should be built by _build_network")
        self.network = self.network.to(state.device)
    features = self.network(state)
    return {EncoderOutputKeys.PROPRIOCEPTIVE.value: features}

get_output_dims

get_output_dims()

Get output dimensions.

Source code in src/versatil/models/encoding/encoders/proprioceptive/base.py
def get_output_dims(self) -> dict[str, int]:
    """Get output dimensions."""
    return {EncoderOutputKeys.PROPRIOCEPTIVE.value: self.output_dim}

validate_input_metadata

validate_input_metadata(key, metadata)

Validate that input metadata is not camera metadata.

Parameters:

Name Type Description Default
key str

Observation key being validated.

required
metadata BaseMetadata

Metadata from the observation space.

required

Returns:

Type Description
str | None

Error message if incompatible, None if valid.

Source code in src/versatil/models/encoding/encoders/proprioceptive/base.py
def validate_input_metadata(self, key: str, metadata: BaseMetadata) -> str | None:
    """Validate that input metadata is not camera metadata.

    Args:
        key: Observation key being validated.
        metadata: Metadata from the observation space.

    Returns:
        Error message if incompatible, None if valid.
    """
    if isinstance(metadata, CameraMetadata):
        return (
            f"ProprioceptiveEncoder cannot process image data for '{key}'. "
            f"Got CameraMetadata, expected proprioceptive state input."
        )
    return None

get_output_specification

get_output_specification()

Get structured output specification with feature names and dimensions.

Returns:

Type Description
list[FeatureMetadata]

List of FeatureMetadata with proprioceptive feature and dimension.

Source code in src/versatil/models/encoding/encoders/proprioceptive/base.py
def get_output_specification(self) -> list[FeatureMetadata]:
    """Get structured output specification with feature names and dimensions.

    Returns:
        List of FeatureMetadata with proprioceptive feature and dimension.
    """
    return [
        FeatureMetadata(
            key=EncoderOutputKeys.PROPRIOCEPTIVE.value,
            feature_type=FeatureType.FLAT.value,
            dimension=(self.output_dim,),
        )
    ]