Rigid Body Dynamics Library
LuaModel example

Here is an example on how to use the Lua Models Addon both for loading the models from C++ code and also how the model file looks like.

Using Lua as a description format for models instead of C++ code has numerous advantages such as simplified modeling, less C++ compilations, and easier exchange of models between multiple users. As the file format uses Lua code it is easy to create parameterized models.

To be able to use the addon one has to enable the addon in CMake by setting BUILD_ADDON_LUAMODEL to true.

Here is an example how Lua Models can be loaded by the RBDL:

/*
* RBDL - Rigid Body Dynamics Library
* Copyright (c) 2011-2018 Martin Felis <martin@fysx.org>
*
* Licensed under the zlib license. See LICENSE for more details.
*/
#include <iostream>
#include <rbdl/rbdl.h>
#ifndef RBDL_BUILD_ADDON_LUAMODEL
#error "Error: RBDL addon LuaModel not enabled."
#endif
using namespace RigidBodyDynamics;
using namespace RigidBodyDynamics::Math;
int main (int argc, char* argv[]) {
rbdl_check_api_version (RBDL_API_VERSION);
Model* model = NULL;
model = new Model();
if (argc != 2) {
std::cerr << "Error: Invalid number of arguments." << std::endl;
std::cerr << "usage: " << argv[0] << " <model.lua>" << std::endl;
exit(-1);
}
if (!Addons::LuaModelReadFromFile (argv[1], model, false)) {
std::cerr << "Error loading model " << argv[1] << std::endl;
abort();
}
std::cout << "Degree of freedom overview:" << std::endl;
std::cout << Utils::GetModelDOFOverview(*model);
std::cout << "Model Hierarchy:" << std::endl;
std::cout << Utils::GetModelHierarchy(*model);
VectorNd Q = VectorNd::Zero (model->q_size);
VectorNd QDot = VectorNd::Zero (model->qdot_size);
VectorNd Tau = VectorNd::Zero (model->qdot_size);
VectorNd QDDot = VectorNd::Zero (model->qdot_size);
std::cout << "Forward Dynamics with q, qdot, tau set to zero:" << std::endl;
ForwardDynamics (*model, Q, QDot, Tau, QDDot);
std::cout << QDDot.transpose() << std::endl;
delete model;
return 0;
}
RBDL_DLLAPI void ForwardDynamics(Model &model, const Math::VectorNd &Q, const Math::VectorNd &QDot, const Math::VectorNd &Tau, Math::VectorNd &QDDot, std::vector< Math::SpatialVector > *f_ext=NULL)
Computes forward dynamics with the Articulated Body Algorithm.
RBDL_ADDON_DLLAPI bool LuaModelReadFromFile(const char *filename, Model *upd_model, bool verbose=false)
Reads a model from a Lua file.
Math types such as vectors and matrices and utility functions.
RBDL_DLLAPI std::string GetModelHierarchy(const Model &model)
Creates a human readable overview of the model.
Definition: rbdl_utils.cc:157
RBDL_DLLAPI std::string GetModelDOFOverview(const Model &model)
Creates a human readable overview of the Degrees of Freedom.
Definition: rbdl_utils.cc:66
RBDL_DLLAPI void rbdl_check_api_version(int version)
Definition: rbdl_version.cc:20

If the library itself is already created, one can compile this example with CMake. In the example folder is a CMakeLists.txt file, that can be used to automatically create the makefiles by using CMake. It uses the script FindRBDL.cmake which can be used to find the library and include directory of the headers.

The documentation about how to write the lua models can be found here.

Here is an example:

--[[
-- This is an example model for the RBDL addon luamodel. You need to
-- enable RBDL_BUILD_ADDON_LUAMODEL to be able to use this file.
--]]
print ("This is some output from the model file")
inertia = {
{1.1, 0.1, 0.2},
{0.3, 1.2, 0.4},
{0.5, 0.6, 1.3}
}
pelvis = { mass = 9.3, com = { 1.1, 1.2, 1.3}, inertia = inertia }
thigh = { mass = 4.2, com = { 1.1, 1.2, 1.3}, inertia = inertia }
shank = { mass = 4.1, com = { 1.1, 1.2, 1.3}, inertia = inertia }
foot = { mass = 1.1, com = { 1.1, 1.2, 1.3}, inertia = inertia }
bodies = {
pelvis = pelvis,
thigh_right = thigh,
shank_right = shank,
thigh_left = thigh,
shank_left = shank
}
joints = {
freeflyer = {
{ 0., 0., 0., 1., 0., 0.},
{ 0., 0., 0., 0., 1., 0.},
{ 0., 0., 0., 0., 0., 1.},
{ 0., 0., 1., 0., 0., 0.},
{ 0., 1., 0., 0., 0., 0.},
{ 1., 0., 0., 0., 0., 0.}
},
spherical_zyx = {
{ 0., 0., 1., 0., 0., 0.},
{ 0., 1., 0., 0., 0., 0.},
{ 1., 0., 0., 0., 0., 0.}
},
rotational_y = {
{ 0., 1., 0., 0., 0., 0.}
},
fixed = {}
}
model = {
gravity = {0., 0., -9.81},
frames = {
{
name = "pelvis",
parent = "ROOT",
body = bodies.pelvis,
joint = joints.freeflyer,
},
{
name = "thigh_right",
parent = "pelvis",
body = bodies.thigh_right,
joint = joints.spherical_zyx,
joint_frame = {
r = {0.0, -0.15, 0.},
E = {
{1., 0., 0.},
{0., 1., 0.},
{0., 0., 0.}
}
}
},
{
name = "shank_right",
parent = "thigh_right",
body = bodies.thigh_right,
joint = joints.rotational_y,
joint_frame = {
r = {0.0, 0., -0.42},
},
},
{
name = "foot_right",
parent = "shank_right",
body = bodies.thigh_right,
joint_frame = {
r = {0.0, 0., -0.41}
},
},
{
name = "thigh_left",
parent = "pelvis",
body = bodies.thigh_left,
joint = joints.spherical_zyx,
joint_frame = {
r = {0.0, 0.15, 0.},
E = {
{1., 0., 0.},
{0., 1., 0.},
{0., 0., 0.}
}
}
},
{
name = "shank_left",
parent = "thigh_left",
body = bodies.thigh_left,
joint = joints.rotational_y,
joint_frame = {
r = {0.0, 0., -0.42},
},
},
{
name = "foot_left",
parent = "shank_left",
body = bodies.thigh_left,
joint_frame = {
r = {0.0, 0., -0.41},
},
},
}
}
return model

The FindRBDL.cmake script can use the environment variables RBDL_PATH, RBDL_INCLUDE_PATH, and RBDL_LIBRARY_PATH to find the required files.

To build it manually you have to specify the following compiler and linking switches:

g++ example.cc -I<path to build folder>/src -I<path to src folder> -lrbdl -L<path to librbdl.a> -o example