Tutorials

All tutorials are jupyter notebooks, downloadable from https://github.com/MarcToussaint/rai-tutorials. For installation instructions, see Getting Started.

The first 3 are intro tutorials that introduce essentials for understanding the code:

  • Configurations: The core data structure used to represent scenes and robots, compute features, and feed into optimization problems, simulations, and real robot control.

  • KOMO: A framework to formulate optimization problems, esp. for motion design (IK, path optimization, and manipulation planning).

  • BotOp: The Robot Operation interface used to control a real or simulated robot, as well as to access sensors.

The remaining tutorials cover various topics in more depth:

More stuff:

from robotic import BSpline
import numpy as np
import matplotlib.pyplot as plt

## B splines themselves, based on uniform knots
S = BSpline()
S.setKnots(2, np.linspace(0.,1.,10))
B = S.getBmatrix(np.linspace(0.,1.,100), False, False)

plt.plot(B)
plt.show()

## setting random control points, and fine-evaluating the resulting spline
X = np.random.randn(10,3)
S.setCtrlPoints(X)
Teval = np.linspace(-.1,1.1,100)
x = S.eval(Teval)
v = S.eval(Teval, 1)
a = S.eval(Teval, 2)

T_X = np.linspace(0.,1.,10)
plt.plot(Teval, np.hstack((x,v/10.,a/100.)))
plt.plot(T_X, X, 'p')
plt.show()

## computing optimal control points that fit the random data X from above
B = S.getBmatrix(T_X, False, True) #start not constrained to zero vel, end is
Z = np.linalg.pinv(B) @ X
S.setCtrlPoints(Z, False, True)
Y = S.eval(Teval)
plt.plot(Teval, Y)
plt.plot(T_X, X, 'p')
plt.show()
# READ THIS: https://www.user.tu-berlin.de/mtoussai/notes/quaternions.pdf
 
from robotic import Quaternion
import math
import numpy as np

q = Quaternion()

print('\n=== using set(...).normalize()):', q.set([1,1,0,0]).normalize())
print('    direct access:', q.w, q.x, q.y, q.z)
print('    as numpy array:', q.asArr())

## converting a quaternion to another representations
print('\n=== converting a quaternion')
print('    original: 90 degree rotation about x:', q)
print('    total rotation angle/pi:', q.getRad()/math.pi)
print('    roll-pitch-yaw/pi:', q.getRollPitchYaw()/math.pi)
print('    log (which is also the "rotation vector"):', q.getLog(), '  length/pi:', np.linalg.norm(q.getLog())/math.pi)
print('    matrix:', q.getMatrix())

## setting a quaternion in various ways:
q = Quaternion()
print('\n=== setting a quaternion')
print('   non-initialized!:', q)
print('   initialize "zero" (which here means identity!)', q.setZero())
print('   the minimal rotation to rotate vector a=(1,0,0) into vector b=(0,1,0)', q.setDiff([1,0,0], [0,1,0]))
print('   90 degrees about the [0,1,0] axis:', q.setRad(math.pi/2, [0,1,0]))
print('   random:', q.setRandom())
print('   exp(log(q)):', q.setExp(q.getLog()))
print('   quat(matrix(q)):', q.setMatrix(q.getMatrix()))
print('   quat(rollPitchWay(q)):', q.setRollPitchYaw(q.getRollPitchYaw()))

## geodesic interpolation
print('\n=== interpolation')
q0 = Quaternion().set([1,1,0,0]).normalize()
q1 = Quaternion().set([1,0,0,1]).normalize()
for t in np.arange(0, 1.1, 0.1):
    q_t = Quaternion().setInterpolateProper(t, q0, q1)
    q_t2 = q0 * Quaternion().setExp(t * ((-q0)*q1).getLog()) #same, but harder to remember
    print(f'   t:{t:.2},  q(t): {q_t},  via exp(log): {q_t2}')

## inverse
print('\n=== multiplication & inverse')
q.setRandom()
print('q:     ', q)
print('q*(-q):', q*(-q))
print('(-q)*q:', (-q)*q)