# *RoMa*: A lightweight library to deal with 3D rotations in PyTorch.
[](https://naver.github.io/roma/)
[](https://badge.fury.io/py/roma)
[](https://arxiv.org/abs/2103.16317)
[](https://github.com/naver/roma/actions/workflows/main.yml)
[](https://pepy.tech/project/roma)
*RoMa* (which stands for Rotation Manipulation) provides differentiable mappings between 3D rotation representations, mappings from Euclidean to rotation space, and various utilities related to rotations.
It is implemented in PyTorch and aims to be an easy-to-use and reasonably efficient toolbox for Machine Learning and gradient-based optimization.
<img src="docsource/source/roma_logo.png" alt="Logo" width="120"/>
## Documentation
Latest documentation is available here: https://naver.github.io/roma/.
Below are some examples of use of *RoMa*:
```python
import torch
import roma
# Arbitrary numbers of batch dimensions are supported, for convenience.
batch_shape = (2, 3)
# Conversion between rotation representations
rotvec = torch.randn(batch_shape + (3,))
q = roma.rotvec_to_unitquat(rotvec)
R = roma.unitquat_to_rotmat(q)
Rbis = roma.rotvec_to_rotmat(rotvec)
euler_angles = roma.unitquat_to_euler('xyz', q, degrees=True)
# Regression of a rotation from an arbitrary input:
# Special Procrustes orthonormalization of a 3x3 matrix
R1 = roma.special_procrustes(torch.randn(batch_shape + (3, 3)))
# Conversion from a 6D representation
R2 = roma.special_gramschmidt(torch.randn(batch_shape + (3, 2)))
# From the 10 coefficients of a 4x4 symmetric matrix
q = roma.symmatrixvec_to_unitquat(torch.randn(batch_shape + (10,)))
# Metrics on the rotation space
R1, R2 = roma.random_rotmat(size=5), roma.random_rotmat(size=5)
theta = roma.utils.rotmat_geodesic_distance(R1, R2)
cos_theta = roma.utils.rotmat_cosine_angle(R1.transpose(-2, -1) @ R2)
# Operations on quaternions
q_identity = roma.quat_product(roma.quat_conjugation(q), q)
# Spherical interpolation between rotation vectors (shortest path)
rotvec0, rotvec1 = torch.randn(batch_shape + (3,)), torch.randn(batch_shape + (3,))
rotvec_interpolated = roma.rotvec_slerp(rotvec0, rotvec1, steps)
# Rigid transformation T composed of a rotation part R and a translation part t
t = torch.randn(batch_shape + (3,))
T = roma.Rigid(R, t)
# Composing and inverting transformations
identity = T @ T.inverse()
# Casting the result to a batch of 4x4 homogeneous matrices
M = identity.to_homogeneous()
```
## Installation
The easiest way to install *RoMa* is to use pip:
```
pip install roma
```
Alternatively one can install the latest version of *RoMa* directly from the source repository:
```
pip install git+https://github.com/naver/roma
```
**With old pytorch versions (torch<1.8)**, we recommend installing [torch-batch-svd](https://github.com/KinglittleQ/torch-batch-svd)
to achieve a significant speed-up with `special_procrustes` on CUDA GPUs.
You can check that this module is properly loaded using the function `roma.utils.is_torch_batch_svd_available()`.
**With recent pytorch installations (torch>=1.8), `torch-batch-svd` is no longer needed or used.**
## License
*RoMa*, Copyright (c) 2020 NAVER Corp., is licensed under the 3-Clause BSD License (see [license](https://github.com/naver/roma/blob/master/LICENSE)).
Bits of code were adapted from SciPy. Documentation is generated, distributed and displayed with the support of Sphinx and other materials (see [notice](https://github.com/naver/roma/blob/master/NOTICE)).
## Contributing
Please open an issue on GitHub if you have any suggestions.
Pull requests are also welcome.
We aim at keeping RoMa reliable and maintainable, and may accept contribution (whether submitted as suggestions or pull requests) at our discretion to that aim.
By contributing to RoMa, you are agreeing that your contributions (whether suggestions or pull requests) for which you have the right or authority to submit are licensed under its [LICENSE](https://github.com/naver/roma/blob/master/LICENSE).
## References
For a more in-depth discussion regarding differentiable mappings on the rotation space, please refer to:
- [__Romain Brégier, Deep Regression on Manifolds: a 3D Rotation Case Study.__ in _2021 International Conference on 3D Vision (3DV)_, 2021.](https://arxiv.org/abs/2103.16317)
Please cite this work in your publications:
```
@inproceedings{bregier2021deepregression,
title={Deep Regression on Manifolds: a {3D} Rotation Case Study},
author={Br{\'e}gier, Romain},
journal={2021 International Conference on 3D Vision (3DV)},
year={2021}
}
```
Raw data
{
"_id": null,
"home_page": "https://github.com/naver/roma",
"name": "roma",
"maintainer": null,
"docs_url": null,
"requires_python": ">=3.6",
"maintainer_email": null,
"keywords": null,
"author": "Romain Br\u00e9gier",
"author_email": "romain.bregier@naverlabs.com",
"download_url": "https://files.pythonhosted.org/packages/32/fd/1e11565d2f3f44db469a7137b9bebcbb42739c7d762051b159792be5633f/roma-1.5.4.tar.gz",
"platform": null,
"description": "\n\n# *RoMa*: A lightweight library to deal with 3D rotations in PyTorch.\n[](https://naver.github.io/roma/)\n[](https://badge.fury.io/py/roma)\n[](https://arxiv.org/abs/2103.16317)\n[](https://github.com/naver/roma/actions/workflows/main.yml)\n[](https://pepy.tech/project/roma)\n\n*RoMa* (which stands for Rotation Manipulation) provides differentiable mappings between 3D rotation representations, mappings from Euclidean to rotation space, and various utilities related to rotations.\n\nIt is implemented in PyTorch and aims to be an easy-to-use and reasonably efficient toolbox for Machine Learning and gradient-based optimization.\n\n<img src=\"docsource/source/roma_logo.png\" alt=\"Logo\" width=\"120\"/>\n\n## Documentation\nLatest documentation is available here: https://naver.github.io/roma/.\n\nBelow are some examples of use of *RoMa*:\n```python\nimport torch\nimport roma\n\n# Arbitrary numbers of batch dimensions are supported, for convenience.\nbatch_shape = (2, 3)\n\n# Conversion between rotation representations\nrotvec = torch.randn(batch_shape + (3,))\nq = roma.rotvec_to_unitquat(rotvec)\nR = roma.unitquat_to_rotmat(q)\nRbis = roma.rotvec_to_rotmat(rotvec)\neuler_angles = roma.unitquat_to_euler('xyz', q, degrees=True)\n\n# Regression of a rotation from an arbitrary input:\n# Special Procrustes orthonormalization of a 3x3 matrix\nR1 = roma.special_procrustes(torch.randn(batch_shape + (3, 3)))\n# Conversion from a 6D representation\nR2 = roma.special_gramschmidt(torch.randn(batch_shape + (3, 2)))\n# From the 10 coefficients of a 4x4 symmetric matrix\nq = roma.symmatrixvec_to_unitquat(torch.randn(batch_shape + (10,)))\n\n# Metrics on the rotation space\nR1, R2 = roma.random_rotmat(size=5), roma.random_rotmat(size=5)\ntheta = roma.utils.rotmat_geodesic_distance(R1, R2)\ncos_theta = roma.utils.rotmat_cosine_angle(R1.transpose(-2, -1) @ R2)\n\n# Operations on quaternions\nq_identity = roma.quat_product(roma.quat_conjugation(q), q)\n\n# Spherical interpolation between rotation vectors (shortest path)\nrotvec0, rotvec1 = torch.randn(batch_shape + (3,)), torch.randn(batch_shape + (3,))\nrotvec_interpolated = roma.rotvec_slerp(rotvec0, rotvec1, steps)\n\n# Rigid transformation T composed of a rotation part R and a translation part t\nt = torch.randn(batch_shape + (3,))\nT = roma.Rigid(R, t)\n# Composing and inverting transformations\nidentity = T @ T.inverse()\n# Casting the result to a batch of 4x4 homogeneous matrices\nM = identity.to_homogeneous()\n```\n\n## Installation\nThe easiest way to install *RoMa* is to use pip:\n```\npip install roma\n```\n\nAlternatively one can install the latest version of *RoMa* directly from the source repository:\n```\npip install git+https://github.com/naver/roma\n```\n\n**With old pytorch versions (torch<1.8)**, we recommend installing [torch-batch-svd](https://github.com/KinglittleQ/torch-batch-svd)\nto achieve a significant speed-up with `special_procrustes` on CUDA GPUs.\nYou can check that this module is properly loaded using the function `roma.utils.is_torch_batch_svd_available()`.\n**With recent pytorch installations (torch>=1.8), `torch-batch-svd` is no longer needed or used.**\n\n\n## License\n*RoMa*, Copyright (c) 2020 NAVER Corp., is licensed under the 3-Clause BSD License (see [license](https://github.com/naver/roma/blob/master/LICENSE)).\n\nBits of code were adapted from SciPy. Documentation is generated, distributed and displayed with the support of Sphinx and other materials (see [notice](https://github.com/naver/roma/blob/master/NOTICE)).\n\n## Contributing\nPlease open an issue on GitHub if you have any suggestions.\nPull requests are also welcome.\nWe aim at keeping RoMa reliable and maintainable, and may accept contribution (whether submitted as suggestions or pull requests) at our discretion to that aim.\n\nBy contributing to RoMa, you are agreeing that your contributions (whether suggestions or pull requests) for which you have the right or authority to submit are licensed under its [LICENSE](https://github.com/naver/roma/blob/master/LICENSE).\n\n## References\nFor a more in-depth discussion regarding differentiable mappings on the rotation space, please refer to:\n- [__Romain Br\u00e9gier, Deep Regression on Manifolds: a 3D Rotation Case Study.__ in _2021 International Conference on 3D Vision (3DV)_, 2021.](https://arxiv.org/abs/2103.16317)\n\nPlease cite this work in your publications:\n```\n@inproceedings{bregier2021deepregression,\n\ttitle={Deep Regression on Manifolds: a {3D} Rotation Case Study},\n\tauthor={Br{\\'e}gier, Romain},\n\tjournal={2021 International Conference on 3D Vision (3DV)},\n\tyear={2021}\n}\n```\n\n",
"bugtrack_url": null,
"license": null,
"summary": "A lightweight library to deal with 3D rotations in PyTorch.",
"version": "1.5.4",
"project_urls": {
"Homepage": "https://github.com/naver/roma"
},
"split_keywords": [],
"urls": [
{
"comment_text": null,
"digests": {
"blake2b_256": "e8e8d571290fa7c1a2beed674d487919efd1fca34d04c3666fdce43eb8bfabed",
"md5": "0ddc84c077d6a435fa2ed9ab09a28d67",
"sha256": "f895bec0be87ab37ce58b65307aa10efa1a7472f42e5b5bff6c0ad74664363f5"
},
"downloads": -1,
"filename": "roma-1.5.4-py3-none-any.whl",
"has_sig": false,
"md5_digest": "0ddc84c077d6a435fa2ed9ab09a28d67",
"packagetype": "bdist_wheel",
"python_version": "py3",
"requires_python": ">=3.6",
"size": 25229,
"upload_time": "2025-07-30T12:27:33",
"upload_time_iso_8601": "2025-07-30T12:27:33.693675Z",
"url": "https://files.pythonhosted.org/packages/e8/e8/d571290fa7c1a2beed674d487919efd1fca34d04c3666fdce43eb8bfabed/roma-1.5.4-py3-none-any.whl",
"yanked": false,
"yanked_reason": null
},
{
"comment_text": null,
"digests": {
"blake2b_256": "32fd1e11565d2f3f44db469a7137b9bebcbb42739c7d762051b159792be5633f",
"md5": "2a97558f4739dc646b9bf9d6ce2849bb",
"sha256": "34d4d731da2b0811d4e6f03cd3f42b52d71c1bb3df7b37db60a5657e2b89d631"
},
"downloads": -1,
"filename": "roma-1.5.4.tar.gz",
"has_sig": false,
"md5_digest": "2a97558f4739dc646b9bf9d6ce2849bb",
"packagetype": "sdist",
"python_version": "source",
"requires_python": ">=3.6",
"size": 31881,
"upload_time": "2025-07-30T12:27:35",
"upload_time_iso_8601": "2025-07-30T12:27:35.061259Z",
"url": "https://files.pythonhosted.org/packages/32/fd/1e11565d2f3f44db469a7137b9bebcbb42739c7d762051b159792be5633f/roma-1.5.4.tar.gz",
"yanked": false,
"yanked_reason": null
}
],
"upload_time": "2025-07-30 12:27:35",
"github": true,
"gitlab": false,
"bitbucket": false,
"codeberg": false,
"github_user": "naver",
"github_project": "roma",
"travis_ci": false,
"coveralls": false,
"github_actions": true,
"requirements": [
{
"name": "torch",
"specs": [
[
">=",
"1.6.0"
]
]
},
{
"name": "numpy",
"specs": []
}
],
"lcname": "roma"
}