HEBI API for MATLAB

 

Many robotics research groups prototype control algorithms and robotic behaviors in MATLAB, and then spend a ton of time on porting the code to another language like C/C++ to test it on a real system. This development cycle is slow, expensive, requires a broad range of programming knowledge and skills, and it is a significant barrier in making meaningful advances in robotics.

The HEBI API for MATLAB lets you prototype directly on real hardware without ever leaving the flexible and powerful MATLAB programming environment.

The API provides several different levels of access to the hardware in order to cover the widest possible range of research projects and applications. Kinematics and trajectory APIs provide high-level control, similar to that of today's industrial robots. Joint-level control APIs allow complete control of each actuator's motion and tight integration of feedback from multiple actuators and external sensors. Lastly, a rich set of logging tools ensures that data can be recorded with virtually no overhead and easily analyzed and visualized, tasks where MATLAB excels.

Want to get some hands-on time and training on the X-Series platform?  Join us at IROS 2017 in Vancouver for our X-Series Workshop.


Setup

The API works out of the box on any operating system that MATLAB runs on. There is no need to install any additional toolboxes and drivers, or to perform additional setup steps. 

The minimum requirements are

  • MATLAB (>=2013b)
  • Network Interface

Joint-Level Control

On the lowest level, we provide an interface that allows synchronized control of the position, velocity, and torque of a group of actuators, as well as receive a rich set of sensor feedback from each actuator. All feedback is returned in SI units and can be requested at rates up to 1KHz.

The below example shows a closed-loop controller that implements a virtual spring that controls torque to drive the output towards the origin (stiffness = 1 Nm / rad).

% Virtual spring on single module
group = HebiLookup.newGroupFromNames('family', 'name');
cmd = CommandStruct();
while true
    fbk = group.getNextFeedback();
    cmd.torque = -fbk.position;
    group.send(cmd);
end

The following example shows an open-loop controller commanding sine waves with different frequencies on two actuators using simultaneous position and velocity control.

% Two actuators executing sine waves of 1Hz and 2Hz
group = HebiLookup.newGroupFromNames('leg', {'knee', 'ankle'});
cmd = CommandStruct();
w = 2 * pi * [1 2];
t0 = tic();
while true
    t = toc(t0);
    cmd.position = sin( w * t );
    cmd.velocity = cos( w * t );
    group.send(cmd);
    pause(0.001);
end

The interface also supports advanced features like gain scheduling, reconfiguring each actuator's internal controllers, and even the ability to bypass all on-board controllers to command motor PWM directly.


Forward and Inverse Kinematics

In addition to low-level control, we also provide an interface that handles the computation of forward and inverse kinematics, Jacobians, as well as methods to compute torques to compensate for joint accelerations and gravity.

% Define kinematic structure using HEBI components
kin = HebiKinematics();
kin.addBody('X5-9');
kin.addBody('X5-LightBracket', 'mounting', 'right');
kin.addBody('X5-4');
kin.addBody('X5-Link', 'extension', 0.350, 'twist', pi/2);
kin.addBody('X5-1');

% Calculate FK
position = [0 0 0];
frames = kin.getForwardKinematics('output', position); 

% Calculate Jacobian for the end effector
J = kin.getJacobian('EndEffector', position)

% Calculate torques for gravity compensation
gravityVec = -[0 0 1];
torque = kin.getGravCompTorques(position, gravityVec);

Combining the kinematics API with the joint-level control API enables advanced behaviors with a minimal amount of coding and complexity. The following example commands a 'weightless' gravity-compensated mode that allows users to touch a robot arm and move it around freely in space. This is often useful control mode for an operator to teach waypoints for teach-repeat applications.

% Determine the direction of gravity based on the
% built-in IMU (assumes fixed base).
fbk = group.getNextFeedback();
gravityVec = -[fbk.accelX(1) fbk.accelY(1) fbk.accelZ(1)];

% Keep the robot in a weight-free teach mode
cmd = CommandStruct();
while true
    fbk = group.getNextFeedback();
    cmd.torque = kin.getGravCompTorques(fbk.position, gravityVec);
    group.send(cmd);
end

Trajectories

We provide built-in trajectories to control a group of actuators in a manner similar to more traditional robot arms.  Features include parameterized minimum-jerk motion, and built-in gravity and dynamics compensation using the kinematics API.

% Setup
trajGen = HebiTrajectoryGenerator(kin);

% Move a group of 3 actuators between two waypoints
start = [0 0 0];
finish = pi/2 * [1 1 1];
trajGen.moveJoint(group, [start; finish]);

For advanced users we include additional hooks that allow for the integration of custom impedance controllers, and non-blocking calls that enable applications to quickly adapt to interactions with the environment or other sensor feedback.


Logging and Visualization

Data logging, visualization, and analysis tools are a critical but often-neglected part of robotics development. We provide powerful logging capabilities that allow the logging of data in excess of 1kHz, from any number of modules, and over extended periods of time (multiple days). Logging is done entirely outside of the main MATLAB thread so that there is no performance impact on real-time control.

% Log data for 5 seconds
group.startLog();
pause(5);
data = group.stopLog();

Logs are returned as structures where data is organized in vectors and matrices so that the resulting data interacts well with MATLAB's built-in plotting tools.

% Plot logged data and overlay commanded and feedback position
figure(); hold on;
plot(data.time, data.position);
plot(data.time, data.positionCmd, ':');

Logs can also be automatically converted to a variety of formats including CSV and MAT files.

% Convert log to mat-file
matFilePath = group.stopLog('FileFormat', 'mat');
data = load(matFilePath);

The logging interface also supports replaying log files in order to simplify unit tests and online algorithm development while working with offline data.

% Iteratively step through log file
group = HebiUtils.newGroupFromLog(path);
while true
    fbk = group.getNextFeedback();
    disp(fbk.position);
end